1 //===-- CommandObjectType.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 //===----------------------------------------------------------------------===//
10 #include "CommandObjectType.h"
18 // Other libraries and framework includes
19 #include "llvm/ADT/StringRef.h"
22 #include "lldb/Core/ConstString.h"
23 #include "lldb/Core/Debugger.h"
24 #include "lldb/Core/IOHandler.h"
25 #include "lldb/Core/RegularExpression.h"
26 #include "lldb/Core/State.h"
27 #include "lldb/Core/StringList.h"
28 #include "lldb/DataFormatters/DataVisualization.h"
29 #include "lldb/Interpreter/CommandInterpreter.h"
30 #include "lldb/Interpreter/CommandObject.h"
31 #include "lldb/Interpreter/CommandReturnObject.h"
32 #include "lldb/Interpreter/Options.h"
33 #include "lldb/Interpreter/OptionGroupFormat.h"
34 #include "lldb/Interpreter/OptionValueBoolean.h"
35 #include "lldb/Interpreter/OptionValueLanguage.h"
36 #include "lldb/Interpreter/OptionValueString.h"
37 #include "lldb/Symbol/Symbol.h"
38 #include "lldb/Target/Language.h"
39 #include "lldb/Target/Process.h"
40 #include "lldb/Target/StackFrame.h"
41 #include "lldb/Target/Target.h"
42 #include "lldb/Target/Thread.h"
43 #include "lldb/Target/ThreadList.h"
46 using namespace lldb_private;
48 class ScriptAddOptions
51 TypeSummaryImpl::Flags m_flags;
52 StringList m_target_types;
55 std::string m_category;
57 ScriptAddOptions(const TypeSummaryImpl::Flags& flags,
59 const ConstString& name,
68 typedef std::shared_ptr<ScriptAddOptions> SharedPointer;
75 bool m_skip_references;
78 StringList m_target_types;
79 std::string m_category;
81 SynthAddOptions(bool sptr,
86 m_skip_pointers(sptr),
87 m_skip_references(sref),
95 typedef std::shared_ptr<SynthAddOptions> SharedPointer;
99 WarnOnPotentialUnquotedUnsignedType (Args& command, CommandReturnObject &result)
101 for (unsigned idx = 0; idx < command.GetArgumentCount(); idx++)
103 const char* arg = command.GetArgumentAtIndex(idx);
104 if (idx+1 < command.GetArgumentCount())
106 if (arg && 0 == strcmp(arg,"unsigned"))
108 const char* next = command.GetArgumentAtIndex(idx+1);
110 (0 == strcmp(next, "int") ||
111 0 == strcmp(next, "short") ||
112 0 == strcmp(next, "char") ||
113 0 == strcmp(next, "long")))
115 result.AppendWarningWithFormat("%s %s being treated as two types. if you meant the combined type name use quotes, as in \"%s %s\"\n",
125 class CommandObjectTypeSummaryAdd :
126 public CommandObjectParsed,
127 public IOHandlerDelegateMultiline
130 class CommandOptions : public Options
133 CommandOptions (CommandInterpreter &interpreter) :
134 Options (interpreter)
138 ~CommandOptions() override = default;
141 SetOptionValue (uint32_t option_idx, const char *option_arg) override;
144 OptionParsingStarting () override;
146 const OptionDefinition*
147 GetDefinitions () override
149 return g_option_table;
152 // Options table: Required for subclasses of Options.
154 static OptionDefinition g_option_table[];
156 // Instance variables to hold the values for command options.
158 TypeSummaryImpl::Flags m_flags;
160 std::string m_format_string;
162 std::string m_python_script;
163 std::string m_python_function;
164 bool m_is_add_script;
165 std::string m_category;
168 CommandOptions m_options;
171 GetOptions () override
177 Execute_ScriptSummary (Args& command, CommandReturnObject &result);
180 Execute_StringSummary (Args& command, CommandReturnObject &result);
183 enum SummaryFormatType
190 CommandObjectTypeSummaryAdd (CommandInterpreter &interpreter);
192 ~CommandObjectTypeSummaryAdd() override = default;
195 IOHandlerActivated (IOHandler &io_handler) override
197 static const char *g_summary_addreader_instructions = "Enter your Python command(s). Type 'DONE' to end.\n"
198 "def function (valobj,internal_dict):\n"
199 " \"\"\"valobj: an SBValue which you want to provide a summary for\n"
200 " internal_dict: an LLDB support object not to be used\"\"\"\n";
202 StreamFileSP output_sp(io_handler.GetOutputStreamFile());
205 output_sp->PutCString(g_summary_addreader_instructions);
211 IOHandlerInputComplete (IOHandler &io_handler, std::string &data) override
213 StreamFileSP error_sp = io_handler.GetErrorStreamFile();
215 #ifndef LLDB_DISABLE_PYTHON
216 ScriptInterpreter *interpreter = m_interpreter.GetScriptInterpreter();
220 lines.SplitIntoLines(data);
221 if (lines.GetSize() > 0)
223 ScriptAddOptions *options_ptr = ((ScriptAddOptions*)io_handler.GetUserData());
226 ScriptAddOptions::SharedPointer options(options_ptr); // this will ensure that we get rid of the pointer when going out of scope
228 ScriptInterpreter *interpreter = m_interpreter.GetScriptInterpreter();
231 std::string funct_name_str;
232 if (interpreter->GenerateTypeScriptFunction (lines, funct_name_str))
234 if (funct_name_str.empty())
236 error_sp->Printf ("unable to obtain a valid function name from the script interpreter.\n");
241 // now I have a valid function name, let's add this as script for every type in the list
243 TypeSummaryImplSP script_format;
244 script_format.reset(new ScriptSummaryFormat(options->m_flags,
245 funct_name_str.c_str(),
246 lines.CopyList(" ").c_str()));
250 for (size_t i = 0; i < options->m_target_types.GetSize(); i++)
252 const char *type_name = options->m_target_types.GetStringAtIndex(i);
253 CommandObjectTypeSummaryAdd::AddSummary(ConstString(type_name),
255 (options->m_regex ? CommandObjectTypeSummaryAdd::eRegexSummary : CommandObjectTypeSummaryAdd::eRegularSummary),
260 error_sp->Printf ("error: %s", error.AsCString());
267 CommandObjectTypeSummaryAdd::AddSummary (options->m_name,
269 CommandObjectTypeSummaryAdd::eNamedSummary,
274 CommandObjectTypeSummaryAdd::AddSummary (options->m_name,
276 CommandObjectTypeSummaryAdd::eNamedSummary,
281 error_sp->Printf ("error: %s", error.AsCString());
287 error_sp->Printf ("error: %s", error.AsCString());
293 if (error.AsCString())
295 error_sp->Printf ("error: %s", error.AsCString());
303 error_sp->Printf ("error: unable to generate a function.\n");
309 error_sp->Printf ("error: no script interpreter.\n");
315 error_sp->Printf ("error: internal synchronization information missing or invalid.\n");
321 error_sp->Printf ("error: empty function, didn't add python command.\n");
327 error_sp->Printf ("error: script interpreter missing, didn't add python command.\n");
330 #endif // LLDB_DISABLE_PYTHON
331 io_handler.SetIsDone(true);
335 AddSummary(ConstString type_name,
336 lldb::TypeSummaryImplSP entry,
337 SummaryFormatType type,
338 std::string category,
339 Error* error = nullptr);
343 DoExecute (Args& command, CommandReturnObject &result) override;
346 static const char *g_synth_addreader_instructions = "Enter your Python command(s). Type 'DONE' to end.\n"
347 "You must define a Python class with these methods:\n"
348 " def __init__(self, valobj, dict):\n"
349 " def num_children(self):\n"
350 " def get_child_at_index(self, index):\n"
351 " def get_child_index(self, name):\n"
352 " def update(self):\n"
354 "class synthProvider:\n";
356 class CommandObjectTypeSynthAdd :
357 public CommandObjectParsed,
358 public IOHandlerDelegateMultiline
361 class CommandOptions : public Options
364 CommandOptions (CommandInterpreter &interpreter) :
365 Options (interpreter)
369 ~CommandOptions() override = default;
372 SetOptionValue (uint32_t option_idx, const char *option_arg) override
375 const int short_option = m_getopt_table[option_idx].val;
378 switch (short_option)
381 m_cascade = Args::StringToBoolean(option_arg, true, &success);
383 error.SetErrorStringWithFormat("invalid value for cascade: %s", option_arg);
386 handwrite_python = true;
389 m_class_name = std::string(option_arg);
390 is_class_based = true;
393 m_skip_pointers = true;
396 m_skip_references = true;
399 m_category = std::string(option_arg);
405 error.SetErrorStringWithFormat ("unrecognized option '%c'", short_option);
413 OptionParsingStarting () override
417 m_skip_pointers = false;
418 m_skip_references = false;
419 m_category = "default";
420 is_class_based = false;
421 handwrite_python = false;
425 const OptionDefinition*
426 GetDefinitions () override
428 return g_option_table;
431 // Options table: Required for subclasses of Options.
433 static OptionDefinition g_option_table[];
435 // Instance variables to hold the values for command options.
438 bool m_skip_references;
439 bool m_skip_pointers;
440 std::string m_class_name;
442 std::string m_category;
444 bool handwrite_python;
448 CommandOptions m_options;
451 GetOptions () override
457 Execute_HandwritePython (Args& command, CommandReturnObject &result);
460 Execute_PythonClass (Args& command, CommandReturnObject &result);
464 DoExecute (Args& command, CommandReturnObject &result) override
466 WarnOnPotentialUnquotedUnsignedType(command, result);
468 if (m_options.handwrite_python)
469 return Execute_HandwritePython(command, result);
470 else if (m_options.is_class_based)
471 return Execute_PythonClass(command, result);
474 result.AppendError("must either provide a children list, a Python class name, or use -P and type a Python class line-by-line");
475 result.SetStatus(eReturnStatusFailed);
481 IOHandlerActivated (IOHandler &io_handler) override
483 StreamFileSP output_sp(io_handler.GetOutputStreamFile());
486 output_sp->PutCString(g_synth_addreader_instructions);
492 IOHandlerInputComplete (IOHandler &io_handler, std::string &data) override
494 StreamFileSP error_sp = io_handler.GetErrorStreamFile();
496 #ifndef LLDB_DISABLE_PYTHON
497 ScriptInterpreter *interpreter = m_interpreter.GetScriptInterpreter();
501 lines.SplitIntoLines(data);
502 if (lines.GetSize() > 0)
504 SynthAddOptions *options_ptr = ((SynthAddOptions*)io_handler.GetUserData());
507 SynthAddOptions::SharedPointer options(options_ptr); // this will ensure that we get rid of the pointer when going out of scope
509 ScriptInterpreter *interpreter = m_interpreter.GetScriptInterpreter();
512 std::string class_name_str;
513 if (interpreter->GenerateTypeSynthClass (lines, class_name_str))
515 if (class_name_str.empty())
517 error_sp->Printf ("error: unable to obtain a proper name for the class.\n");
522 // everything should be fine now, let's add the synth provider class
524 SyntheticChildrenSP synth_provider;
525 synth_provider.reset(new ScriptedSyntheticChildren(SyntheticChildren::Flags().SetCascades(options->m_cascade).
526 SetSkipPointers(options->m_skip_pointers).
527 SetSkipReferences(options->m_skip_references),
528 class_name_str.c_str()));
531 lldb::TypeCategoryImplSP category;
532 DataVisualization::Categories::GetCategory(ConstString(options->m_category.c_str()), category);
536 for (size_t i = 0; i < options->m_target_types.GetSize(); i++)
538 const char *type_name = options->m_target_types.GetStringAtIndex(i);
539 ConstString const_type_name(type_name);
542 if (!CommandObjectTypeSynthAdd::AddSynth(const_type_name,
544 options->m_regex ? CommandObjectTypeSynthAdd::eRegexSynth : CommandObjectTypeSynthAdd::eRegularSynth,
548 error_sp->Printf("error: %s\n", error.AsCString());
555 error_sp->Printf ("error: invalid type name.\n");
564 error_sp->Printf ("error: unable to generate a class.\n");
570 error_sp->Printf ("error: no script interpreter.\n");
576 error_sp->Printf ("error: internal synchronization data missing.\n");
582 error_sp->Printf ("error: empty function, didn't add python command.\n");
588 error_sp->Printf ("error: script interpreter missing, didn't add python command.\n");
592 #endif // LLDB_DISABLE_PYTHON
593 io_handler.SetIsDone(true);
603 CommandObjectTypeSynthAdd (CommandInterpreter &interpreter);
605 ~CommandObjectTypeSynthAdd() override = default;
608 AddSynth(ConstString type_name,
609 lldb::SyntheticChildrenSP entry,
610 SynthFormatType type,
611 std::string category_name,
615 //-------------------------------------------------------------------------
616 // CommandObjectTypeFormatAdd
617 //-------------------------------------------------------------------------
619 class CommandObjectTypeFormatAdd : public CommandObjectParsed
622 class CommandOptions : public OptionGroup
630 ~CommandOptions() override = default;
633 GetNumDefinitions () override;
635 const OptionDefinition*
636 GetDefinitions () override
638 return g_option_table;
642 OptionParsingStarting (CommandInterpreter &interpreter) override
645 m_skip_pointers = false;
646 m_skip_references = false;
648 m_category.assign("default");
649 m_custom_type_name.clear();
653 SetOptionValue (CommandInterpreter &interpreter,
655 const char *option_value) override
658 const int short_option = g_option_table[option_idx].short_option;
661 switch (short_option)
664 m_cascade = Args::StringToBoolean(option_value, true, &success);
666 error.SetErrorStringWithFormat("invalid value for cascade: %s", option_value);
669 m_skip_pointers = true;
672 m_category.assign(option_value);
675 m_skip_references = true;
681 m_custom_type_name.assign(option_value);
684 error.SetErrorStringWithFormat ("unrecognized option '%c'", short_option);
691 // Options table: Required for subclasses of Options.
693 static OptionDefinition g_option_table[];
695 // Instance variables to hold the values for command options.
698 bool m_skip_references;
699 bool m_skip_pointers;
701 std::string m_category;
702 std::string m_custom_type_name;
705 OptionGroupOptions m_option_group;
706 OptionGroupFormat m_format_options;
707 CommandOptions m_command_options;
710 GetOptions () override
712 return &m_option_group;
716 CommandObjectTypeFormatAdd (CommandInterpreter &interpreter) :
717 CommandObjectParsed(interpreter,
719 "Add a new formatting style for a type.",
721 m_option_group (interpreter),
722 m_format_options (eFormatInvalid),
725 CommandArgumentEntry type_arg;
726 CommandArgumentData type_style_arg;
728 type_style_arg.arg_type = eArgTypeName;
729 type_style_arg.arg_repetition = eArgRepeatPlus;
731 type_arg.push_back (type_style_arg);
733 m_arguments.push_back (type_arg);
737 The following examples of 'type format add' refer to this code snippet for context:
740 typedef float Afloat;
742 typedef Afloat Bfloat;
750 Adding default formatting:
752 (lldb) type format add -f hex AInt
753 (lldb) frame variable iy
755 )" " Produces hexidecimal display of iy, because no formatter is available for Bint and \
756 the one for Aint is used instead." R"(
758 To prevent this use the cascade option '-C no' to prevent evaluation of typedef chains:
761 (lldb) type format add -f hex -C no AInt
763 Similar reasoning applies to this:
765 (lldb) type format add -f hex -C no float -p
767 )" " All float values and float references are now formatted as hexadecimal, but not \
768 pointers to floats. Nor will it change the default display for Afloat and Bfloat objects."
771 // Add the "--format" to all options groups
772 m_option_group.Append (&m_format_options, OptionGroupFormat::OPTION_GROUP_FORMAT, LLDB_OPT_SET_1);
773 m_option_group.Append (&m_command_options);
774 m_option_group.Finalize();
777 ~CommandObjectTypeFormatAdd() override = default;
781 DoExecute (Args& command, CommandReturnObject &result) override
783 const size_t argc = command.GetArgumentCount();
787 result.AppendErrorWithFormat ("%s takes one or more args.\n", m_cmd_name.c_str());
788 result.SetStatus(eReturnStatusFailed);
792 const Format format = m_format_options.GetFormat();
793 if (format == eFormatInvalid && m_command_options.m_custom_type_name.empty())
795 result.AppendErrorWithFormat ("%s needs a valid format.\n", m_cmd_name.c_str());
796 result.SetStatus(eReturnStatusFailed);
800 TypeFormatImplSP entry;
802 if (m_command_options.m_custom_type_name.empty())
803 entry.reset(new TypeFormatImpl_Format(format,
804 TypeFormatImpl::Flags().SetCascades(m_command_options.m_cascade).
805 SetSkipPointers(m_command_options.m_skip_pointers).
806 SetSkipReferences(m_command_options.m_skip_references)));
808 entry.reset(new TypeFormatImpl_EnumType(ConstString(m_command_options.m_custom_type_name.c_str()),
809 TypeFormatImpl::Flags().SetCascades(m_command_options.m_cascade).
810 SetSkipPointers(m_command_options.m_skip_pointers).
811 SetSkipReferences(m_command_options.m_skip_references)));
813 // now I have a valid format, let's add it to every type
815 TypeCategoryImplSP category_sp;
816 DataVisualization::Categories::GetCategory(ConstString(m_command_options.m_category), category_sp);
820 WarnOnPotentialUnquotedUnsignedType(command, result);
822 for (size_t i = 0; i < argc; i++)
824 const char* typeA = command.GetArgumentAtIndex(i);
825 ConstString typeCS(typeA);
828 if (m_command_options.m_regex)
830 RegularExpressionSP typeRX(new RegularExpression());
831 if (!typeRX->Compile(typeCS.GetCString()))
833 result.AppendError("regex format error (maybe this is not really a regex?)");
834 result.SetStatus(eReturnStatusFailed);
837 category_sp->GetRegexTypeSummariesContainer()->Delete(typeCS);
838 category_sp->GetRegexTypeFormatsContainer()->Add(typeRX, entry);
841 category_sp->GetTypeFormatsContainer()->Add(typeCS, entry);
845 result.AppendError("empty typenames not allowed");
846 result.SetStatus(eReturnStatusFailed);
851 result.SetStatus(eReturnStatusSuccessFinishNoResult);
852 return result.Succeeded();
857 CommandObjectTypeFormatAdd::CommandOptions::g_option_table[] =
859 { LLDB_OPT_SET_ALL, false, "category", 'w', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeName, "Add this to the given category instead of the default one."},
860 { LLDB_OPT_SET_ALL, false, "cascade", 'C', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeBoolean, "If true, cascade through typedef chains."},
861 { LLDB_OPT_SET_ALL, false, "skip-pointers", 'p', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Don't use this format for pointers-to-type objects."},
862 { LLDB_OPT_SET_ALL, false, "skip-references", 'r', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Don't use this format for references-to-type objects."},
863 { LLDB_OPT_SET_ALL, false, "regex", 'x', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Type names are actually regular expressions."},
864 { LLDB_OPT_SET_2, false, "type", 't', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeName, "Format variables as if they were of this type."},
865 { 0, false, nullptr, 0, 0, nullptr, nullptr, 0, eArgTypeNone, nullptr }
869 CommandObjectTypeFormatAdd::CommandOptions::GetNumDefinitions ()
871 return sizeof(g_option_table) / sizeof (OptionDefinition);
874 class CommandObjectTypeFormatterDelete : public CommandObjectParsed
877 class CommandOptions : public Options
880 CommandOptions (CommandInterpreter &interpreter) :
881 Options (interpreter)
885 ~CommandOptions() override = default;
888 SetOptionValue (uint32_t option_idx, const char *option_arg) override
891 const int short_option = m_getopt_table[option_idx].val;
893 switch (short_option)
899 m_category = std::string(option_arg);
902 m_language = Language::GetLanguageTypeFromString(option_arg);
905 error.SetErrorStringWithFormat ("unrecognized option '%c'", short_option);
913 OptionParsingStarting () override
915 m_delete_all = false;
916 m_category = "default";
917 m_language = lldb::eLanguageTypeUnknown;
920 const OptionDefinition*
921 GetDefinitions () override
923 return g_option_table;
926 // Options table: Required for subclasses of Options.
928 static OptionDefinition g_option_table[];
930 // Instance variables to hold the values for command options.
933 std::string m_category;
934 lldb::LanguageType m_language;
937 CommandOptions m_options;
938 uint32_t m_formatter_kind_mask;
941 GetOptions () override
947 CommandObjectTypeFormatterDelete (CommandInterpreter &interpreter,
948 uint32_t formatter_kind_mask,
951 CommandObjectParsed(interpreter,
955 m_options(interpreter),
956 m_formatter_kind_mask(formatter_kind_mask)
958 CommandArgumentEntry type_arg;
959 CommandArgumentData type_style_arg;
961 type_style_arg.arg_type = eArgTypeName;
962 type_style_arg.arg_repetition = eArgRepeatPlain;
964 type_arg.push_back (type_style_arg);
966 m_arguments.push_back (type_arg);
969 ~CommandObjectTypeFormatterDelete() override = default;
973 FormatterSpecificDeletion (ConstString typeCS)
979 DoExecute (Args& command, CommandReturnObject &result) override
981 const size_t argc = command.GetArgumentCount();
985 result.AppendErrorWithFormat ("%s takes 1 arg.\n", m_cmd_name.c_str());
986 result.SetStatus(eReturnStatusFailed);
990 const char* typeA = command.GetArgumentAtIndex(0);
991 ConstString typeCS(typeA);
995 result.AppendError("empty typenames not allowed");
996 result.SetStatus(eReturnStatusFailed);
1000 if (m_options.m_delete_all)
1002 DataVisualization::Categories::ForEach( [this, typeCS] (const lldb::TypeCategoryImplSP& category_sp) -> bool {
1003 category_sp->Delete(typeCS, m_formatter_kind_mask);
1006 result.SetStatus(eReturnStatusSuccessFinishNoResult);
1007 return result.Succeeded();
1010 bool delete_category = false;
1011 bool extra_deletion = false;
1013 if (m_options.m_language != lldb::eLanguageTypeUnknown)
1015 lldb::TypeCategoryImplSP category;
1016 DataVisualization::Categories::GetCategory(m_options.m_language, category);
1018 delete_category = category->Delete(typeCS, m_formatter_kind_mask);
1019 extra_deletion = FormatterSpecificDeletion(typeCS);
1023 lldb::TypeCategoryImplSP category;
1024 DataVisualization::Categories::GetCategory(ConstString(m_options.m_category.c_str()), category);
1026 delete_category = category->Delete(typeCS, m_formatter_kind_mask);
1027 extra_deletion = FormatterSpecificDeletion(typeCS);
1030 if (delete_category || extra_deletion)
1032 result.SetStatus(eReturnStatusSuccessFinishNoResult);
1033 return result.Succeeded();
1037 result.AppendErrorWithFormat ("no custom formatter for %s.\n", typeA);
1038 result.SetStatus(eReturnStatusFailed);
1045 CommandObjectTypeFormatterDelete::CommandOptions::g_option_table[] =
1047 { LLDB_OPT_SET_1, false, "all", 'a', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Delete from every category."},
1048 { LLDB_OPT_SET_2, false, "category", 'w', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeName, "Delete from given category."},
1049 { LLDB_OPT_SET_3, false, "language", 'l', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeLanguage, "Delete from given language's category."},
1050 { 0, false, nullptr, 0, 0, nullptr, nullptr, 0, eArgTypeNone, nullptr }
1053 class CommandObjectTypeFormatterClear : public CommandObjectParsed
1056 class CommandOptions : public Options
1059 CommandOptions (CommandInterpreter &interpreter) :
1060 Options (interpreter)
1064 ~CommandOptions() override = default;
1067 SetOptionValue (uint32_t option_idx, const char *option_arg) override
1070 const int short_option = m_getopt_table[option_idx].val;
1072 switch (short_option)
1075 m_delete_all = true;
1078 error.SetErrorStringWithFormat ("unrecognized option '%c'", short_option);
1086 OptionParsingStarting () override
1088 m_delete_all = false;
1091 const OptionDefinition*
1092 GetDefinitions () override
1094 return g_option_table;
1097 // Options table: Required for subclasses of Options.
1099 static OptionDefinition g_option_table[];
1101 // Instance variables to hold the values for command options.
1105 CommandOptions m_options;
1106 uint32_t m_formatter_kind_mask;
1109 GetOptions () override
1115 CommandObjectTypeFormatterClear (CommandInterpreter &interpreter,
1116 uint32_t formatter_kind_mask,
1119 CommandObjectParsed(interpreter,
1123 m_options(interpreter),
1124 m_formatter_kind_mask(formatter_kind_mask)
1128 ~CommandObjectTypeFormatterClear() override = default;
1132 FormatterSpecificDeletion ()
1137 DoExecute (Args& command, CommandReturnObject &result) override
1139 if (m_options.m_delete_all)
1141 DataVisualization::Categories::ForEach( [this] (const TypeCategoryImplSP& category_sp) -> bool {
1142 category_sp->Clear(m_formatter_kind_mask);
1148 lldb::TypeCategoryImplSP category;
1149 if (command.GetArgumentCount() > 0)
1151 const char* cat_name = command.GetArgumentAtIndex(0);
1152 ConstString cat_nameCS(cat_name);
1153 DataVisualization::Categories::GetCategory(cat_nameCS, category);
1157 DataVisualization::Categories::GetCategory(ConstString(nullptr), category);
1159 category->Clear(m_formatter_kind_mask);
1162 FormatterSpecificDeletion();
1164 result.SetStatus(eReturnStatusSuccessFinishResult);
1165 return result.Succeeded();
1170 CommandObjectTypeFormatterClear::CommandOptions::g_option_table[] =
1172 { LLDB_OPT_SET_ALL, false, "all", 'a', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Clear every category."},
1173 { 0, false, nullptr, 0, 0, nullptr, nullptr, 0, eArgTypeNone, nullptr }
1176 //-------------------------------------------------------------------------
1177 // CommandObjectTypeFormatDelete
1178 //-------------------------------------------------------------------------
1180 class CommandObjectTypeFormatDelete : public CommandObjectTypeFormatterDelete
1183 CommandObjectTypeFormatDelete (CommandInterpreter &interpreter) :
1184 CommandObjectTypeFormatterDelete (interpreter,
1185 eFormatCategoryItemValue | eFormatCategoryItemRegexValue,
1186 "type format delete",
1187 "Delete an existing formatting style for a type.")
1191 ~CommandObjectTypeFormatDelete() override = default;
1194 //-------------------------------------------------------------------------
1195 // CommandObjectTypeFormatClear
1196 //-------------------------------------------------------------------------
1198 class CommandObjectTypeFormatClear : public CommandObjectTypeFormatterClear
1201 CommandObjectTypeFormatClear (CommandInterpreter &interpreter) :
1202 CommandObjectTypeFormatterClear (interpreter,
1203 eFormatCategoryItemValue | eFormatCategoryItemRegexValue,
1204 "type format clear",
1205 "Delete all existing format styles.")
1210 template <typename FormatterType>
1211 class CommandObjectTypeFormatterList : public CommandObjectParsed
1213 typedef typename FormatterType::SharedPointer FormatterSharedPointer;
1215 class CommandOptions : public Options
1218 CommandOptions (CommandInterpreter &interpreter) :
1219 Options (interpreter),
1220 m_category_regex("",""),
1221 m_category_language(lldb::eLanguageTypeUnknown, lldb::eLanguageTypeUnknown)
1225 ~CommandOptions() override = default;
1228 SetOptionValue (uint32_t option_idx, const char *option_arg) override
1231 const int short_option = m_getopt_table[option_idx].val;
1233 switch (short_option)
1236 m_category_regex.SetCurrentValue(option_arg);
1237 m_category_regex.SetOptionWasSet();
1240 error = m_category_language.SetValueFromString(option_arg);
1241 if (error.Success())
1242 m_category_language.SetOptionWasSet();
1245 error.SetErrorStringWithFormat ("unrecognized option '%c'", short_option);
1253 OptionParsingStarting () override
1255 m_category_regex.Clear();
1256 m_category_language.Clear();
1259 const OptionDefinition*
1260 GetDefinitions () override
1262 static OptionDefinition g_option_table[] =
1264 { LLDB_OPT_SET_1, false, "category-regex", 'w', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeName, "Only show categories matching this filter."},
1265 { LLDB_OPT_SET_2, false, "language", 'l', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeLanguage, "Only show the category for a specific language."},
1266 { 0, false, nullptr, 0, 0, nullptr, nullptr, 0, eArgTypeNone, nullptr }
1269 return g_option_table;
1272 // Options table: Required for subclasses of Options.
1274 static OptionDefinition g_option_table[];
1276 // Instance variables to hold the values for command options.
1278 OptionValueString m_category_regex;
1279 OptionValueLanguage m_category_language;
1282 CommandOptions m_options;
1285 GetOptions () override
1291 CommandObjectTypeFormatterList (CommandInterpreter &interpreter,
1294 CommandObjectParsed(interpreter,
1298 m_options(interpreter)
1300 CommandArgumentEntry type_arg;
1301 CommandArgumentData type_style_arg;
1303 type_style_arg.arg_type = eArgTypeName;
1304 type_style_arg.arg_repetition = eArgRepeatOptional;
1306 type_arg.push_back (type_style_arg);
1308 m_arguments.push_back (type_arg);
1311 ~CommandObjectTypeFormatterList() override = default;
1315 FormatterSpecificList (CommandReturnObject &result)
1321 DoExecute (Args& command, CommandReturnObject &result) override
1323 const size_t argc = command.GetArgumentCount();
1325 std::unique_ptr<RegularExpression> category_regex;
1326 std::unique_ptr<RegularExpression> formatter_regex;
1328 if (m_options.m_category_regex.OptionWasSet())
1330 category_regex.reset(new RegularExpression());
1331 if (!category_regex->Compile(m_options.m_category_regex.GetCurrentValue()))
1333 result.AppendErrorWithFormat("syntax error in category regular expression '%s'", m_options.m_category_regex.GetCurrentValue());
1334 result.SetStatus(eReturnStatusFailed);
1341 const char* arg = command.GetArgumentAtIndex(0);
1342 formatter_regex.reset(new RegularExpression());
1343 if (!formatter_regex->Compile(arg))
1345 result.AppendErrorWithFormat("syntax error in regular expression '%s'", arg);
1346 result.SetStatus(eReturnStatusFailed);
1351 bool any_printed = false;
1353 auto category_closure = [&result, &formatter_regex, &any_printed] (const lldb::TypeCategoryImplSP& category) -> void {
1354 result.GetOutputStream().Printf("-----------------------\nCategory: %s%s\n-----------------------\n",
1355 category->GetName(),
1356 category->IsEnabled() ? "" : " (disabled)");
1358 TypeCategoryImpl::ForEachCallbacks<FormatterType> foreach;
1359 foreach.SetExact([&result, &formatter_regex, &any_printed] (ConstString name, const FormatterSharedPointer& format_sp) -> bool {
1360 if (formatter_regex)
1363 if (0 == strcmp(name.AsCString(), formatter_regex->GetText()))
1367 else if (formatter_regex->Execute(name.AsCString()))
1377 result.GetOutputStream().Printf ("%s: %s\n", name.AsCString(), format_sp->GetDescription().c_str());
1381 foreach.SetWithRegex([&result, &formatter_regex, &any_printed] (RegularExpressionSP regex_sp, const FormatterSharedPointer& format_sp) -> bool {
1382 if (formatter_regex)
1385 if (0 == strcmp(regex_sp->GetText(), formatter_regex->GetText()))
1389 else if (formatter_regex->Execute(regex_sp->GetText()))
1399 result.GetOutputStream().Printf ("%s: %s\n", regex_sp->GetText(), format_sp->GetDescription().c_str());
1403 category->ForEach(foreach);
1406 if (m_options.m_category_language.OptionWasSet())
1408 lldb::TypeCategoryImplSP category_sp;
1409 DataVisualization::Categories::GetCategory(m_options.m_category_language.GetCurrentValue(), category_sp);
1411 category_closure(category_sp);
1415 DataVisualization::Categories::ForEach( [this, &command, &result, &category_regex, &formatter_regex, &category_closure] (const lldb::TypeCategoryImplSP& category) -> bool {
1419 if (0 == strcmp(category->GetName(), category_regex->GetText()))
1423 else if (category_regex->Execute(category->GetName()))
1432 category_closure(category);
1437 any_printed = FormatterSpecificList(result) | any_printed;
1441 result.SetStatus(eReturnStatusSuccessFinishResult);
1444 result.GetOutputStream().PutCString("no matching results found.\n");
1445 result.SetStatus(eReturnStatusSuccessFinishNoResult);
1447 return result.Succeeded();
1451 //-------------------------------------------------------------------------
1452 // CommandObjectTypeFormatList
1453 //-------------------------------------------------------------------------
1455 class CommandObjectTypeFormatList : public CommandObjectTypeFormatterList<TypeFormatImpl>
1459 CommandObjectTypeFormatList (CommandInterpreter &interpreter) :
1460 CommandObjectTypeFormatterList(interpreter,
1462 "Show a list of current formats.")
1467 #ifndef LLDB_DISABLE_PYTHON
1469 //-------------------------------------------------------------------------
1470 // CommandObjectTypeSummaryAdd
1471 //-------------------------------------------------------------------------
1473 #endif // LLDB_DISABLE_PYTHON
1476 CommandObjectTypeSummaryAdd::CommandOptions::SetOptionValue (uint32_t option_idx, const char *option_arg)
1479 const int short_option = m_getopt_table[option_idx].val;
1482 switch (short_option)
1485 m_flags.SetCascades(Args::StringToBoolean(option_arg, true, &success));
1487 error.SetErrorStringWithFormat("invalid value for cascade: %s", option_arg);
1490 m_flags.SetDontShowChildren(false);
1493 m_flags.SetHideEmptyAggregates(true);
1496 m_flags.SetDontShowValue(true);
1499 m_flags.SetShowMembersOneLiner(true);
1502 m_format_string = std::string(option_arg);
1505 m_flags.SetSkipPointers(true);
1508 m_flags.SetSkipReferences(true);
1514 m_name.SetCString(option_arg);
1517 m_python_script = std::string(option_arg);
1518 m_is_add_script = true;
1521 m_python_function = std::string(option_arg);
1522 m_is_add_script = true;
1525 m_is_add_script = true;
1528 m_category = std::string(option_arg);
1531 m_flags.SetHideItemNames(true);
1534 error.SetErrorStringWithFormat ("unrecognized option '%c'", short_option);
1542 CommandObjectTypeSummaryAdd::CommandOptions::OptionParsingStarting ()
1544 m_flags.Clear().SetCascades().SetDontShowChildren().SetDontShowValue(false);
1545 m_flags.SetShowMembersOneLiner(false).SetSkipPointers(false).SetSkipReferences(false).SetHideItemNames(false);
1549 m_python_script = "";
1550 m_python_function = "";
1551 m_format_string = "";
1552 m_is_add_script = false;
1553 m_category = "default";
1556 #ifndef LLDB_DISABLE_PYTHON
1559 CommandObjectTypeSummaryAdd::Execute_ScriptSummary (Args& command, CommandReturnObject &result)
1561 const size_t argc = command.GetArgumentCount();
1563 if (argc < 1 && !m_options.m_name)
1565 result.AppendErrorWithFormat ("%s takes one or more args.\n", m_cmd_name.c_str());
1566 result.SetStatus(eReturnStatusFailed);
1570 TypeSummaryImplSP script_format;
1572 if (!m_options.m_python_function.empty()) // we have a Python function ready to use
1574 const char *funct_name = m_options.m_python_function.c_str();
1575 if (!funct_name || !funct_name[0])
1577 result.AppendError ("function name empty.\n");
1578 result.SetStatus (eReturnStatusFailed);
1582 std::string code = (" " + m_options.m_python_function + "(valobj,internal_dict)");
1584 script_format.reset(new ScriptSummaryFormat(m_options.m_flags,
1588 ScriptInterpreter *interpreter = m_interpreter.GetScriptInterpreter();
1590 if (interpreter && !interpreter->CheckObjectExists(funct_name))
1591 result.AppendWarningWithFormat("The provided function \"%s\" does not exist - "
1592 "please define it before attempting to use this summary.\n",
1595 else if (!m_options.m_python_script.empty()) // we have a quick 1-line script, just use it
1597 ScriptInterpreter *interpreter = m_interpreter.GetScriptInterpreter();
1600 result.AppendError ("script interpreter missing - unable to generate function wrapper.\n");
1601 result.SetStatus (eReturnStatusFailed);
1604 StringList funct_sl;
1605 funct_sl << m_options.m_python_script.c_str();
1606 std::string funct_name_str;
1607 if (!interpreter->GenerateTypeScriptFunction (funct_sl,
1610 result.AppendError ("unable to generate function wrapper.\n");
1611 result.SetStatus (eReturnStatusFailed);
1614 if (funct_name_str.empty())
1616 result.AppendError ("script interpreter failed to generate a valid function name.\n");
1617 result.SetStatus (eReturnStatusFailed);
1621 std::string code = " " + m_options.m_python_script;
1623 script_format.reset(new ScriptSummaryFormat(m_options.m_flags,
1624 funct_name_str.c_str(),
1629 // Use an IOHandler to grab Python code from the user
1630 ScriptAddOptions *options = new ScriptAddOptions(m_options.m_flags,
1633 m_options.m_category);
1635 for (size_t i = 0; i < argc; i++)
1637 const char* typeA = command.GetArgumentAtIndex(i);
1638 if (typeA && *typeA)
1639 options->m_target_types << typeA;
1642 result.AppendError("empty typenames not allowed");
1643 result.SetStatus(eReturnStatusFailed);
1648 m_interpreter.GetPythonCommandsFromIOHandler (" ", // Prompt
1649 *this, // IOHandlerDelegate
1650 true, // Run IOHandler in async mode
1651 options); // Baton for the "io_handler" that will be passed back into our IOHandlerDelegate functions
1652 result.SetStatus(eReturnStatusSuccessFinishNoResult);
1654 return result.Succeeded();
1657 // if I am here, script_format must point to something good, so I can add that
1658 // as a script summary to all interested parties
1662 for (size_t i = 0; i < command.GetArgumentCount(); i++)
1664 const char *type_name = command.GetArgumentAtIndex(i);
1665 CommandObjectTypeSummaryAdd::AddSummary(ConstString(type_name),
1667 (m_options.m_regex ? eRegexSummary : eRegularSummary),
1668 m_options.m_category,
1672 result.AppendError(error.AsCString());
1673 result.SetStatus(eReturnStatusFailed);
1678 if (m_options.m_name)
1680 AddSummary(m_options.m_name, script_format, eNamedSummary, m_options.m_category, &error);
1683 result.AppendError(error.AsCString());
1684 result.AppendError("added to types, but not given a name");
1685 result.SetStatus(eReturnStatusFailed);
1690 return result.Succeeded();
1693 #endif // LLDB_DISABLE_PYTHON
1696 CommandObjectTypeSummaryAdd::Execute_StringSummary (Args& command, CommandReturnObject &result)
1698 const size_t argc = command.GetArgumentCount();
1700 if (argc < 1 && !m_options.m_name)
1702 result.AppendErrorWithFormat ("%s takes one or more args.\n", m_cmd_name.c_str());
1703 result.SetStatus(eReturnStatusFailed);
1707 if (!m_options.m_flags.GetShowMembersOneLiner() && m_options.m_format_string.empty())
1709 result.AppendError("empty summary strings not allowed");
1710 result.SetStatus(eReturnStatusFailed);
1714 const char* format_cstr = (m_options.m_flags.GetShowMembersOneLiner() ? "" : m_options.m_format_string.c_str());
1716 // ${var%S} is an endless recursion, prevent it
1717 if (strcmp(format_cstr, "${var%S}") == 0)
1719 result.AppendError("recursive summary not allowed");
1720 result.SetStatus(eReturnStatusFailed);
1724 std::unique_ptr<StringSummaryFormat> string_format(new StringSummaryFormat(m_options.m_flags, format_cstr));
1727 result.AppendError("summary creation failed");
1728 result.SetStatus(eReturnStatusFailed);
1731 if (string_format->m_error.Fail())
1733 result.AppendErrorWithFormat("syntax error: %s", string_format->m_error.AsCString("<unknown>"));
1734 result.SetStatus(eReturnStatusFailed);
1737 lldb::TypeSummaryImplSP entry(string_format.release());
1739 // now I have a valid format, let's add it to every type
1741 for (size_t i = 0; i < argc; i++)
1743 const char* typeA = command.GetArgumentAtIndex(i);
1744 if (!typeA || typeA[0] == '\0')
1746 result.AppendError("empty typenames not allowed");
1747 result.SetStatus(eReturnStatusFailed);
1750 ConstString typeCS(typeA);
1754 (m_options.m_regex ? eRegexSummary : eRegularSummary),
1755 m_options.m_category,
1760 result.AppendError(error.AsCString());
1761 result.SetStatus(eReturnStatusFailed);
1766 if (m_options.m_name)
1768 AddSummary(m_options.m_name, entry, eNamedSummary, m_options.m_category, &error);
1771 result.AppendError(error.AsCString());
1772 result.AppendError("added to types, but not given a name");
1773 result.SetStatus(eReturnStatusFailed);
1778 result.SetStatus(eReturnStatusSuccessFinishNoResult);
1779 return result.Succeeded();
1782 CommandObjectTypeSummaryAdd::CommandObjectTypeSummaryAdd (CommandInterpreter &interpreter) :
1783 CommandObjectParsed(interpreter,
1785 "Add a new summary style for a type.",
1787 IOHandlerDelegateMultiline ("DONE"),
1788 m_options (interpreter)
1790 CommandArgumentEntry type_arg;
1791 CommandArgumentData type_style_arg;
1793 type_style_arg.arg_type = eArgTypeName;
1794 type_style_arg.arg_repetition = eArgRepeatPlus;
1796 type_arg.push_back (type_style_arg);
1798 m_arguments.push_back (type_arg);
1802 The following examples of 'type summary add' refer to this code snippet for context:
1808 JustADemo(int p = 1, float v = 0.1) : ptr(new int(p)), value(v) {}
1810 JustADemo demo_instance(42, 3.14);
1812 typedef JustADemo NewDemo;
1813 NewDemo new_demo_instance(42, 3.14);
1815 (lldb) type summary add --summary-string "the answer is ${*var.ptr}" JustADemo
1817 Subsequently displaying demo_instance with 'frame variable' or 'expression' will display "the answer is 42"
1819 (lldb) type summary add --summary-string "the answer is ${*var.ptr}, and the question is ${var.value}" JustADemo
1821 Subsequently displaying demo_instance with 'frame variable' or 'expression' will display "the answer is 42 and the question is 3.14"
1823 )" "Alternatively, you could define formatting for all pointers to integers and \
1824 rely on that when formatting JustADemo to obtain the same result:" R"(
1826 (lldb) type summary add --summary-string "${var%V} -> ${*var}" "int *"
1827 (lldb) type summary add --summary-string "the answer is ${var.ptr}, and the question is ${var.value}" JustADemo
1829 )" "Type summaries are automatically applied to derived typedefs, so the examples \
1830 above apply to both JustADemo and NewDemo. The cascade option can be used to \
1831 suppress this behavior:" R"(
1833 (lldb) type summary add --summary-string "${var.ptr}, ${var.value},{${var.byte}}" JustADemo -C no
1835 The summary will now be used for values of JustADemo but not NewDemo.
1837 )" "By default summaries are shown for pointers and references to values of the \
1838 specified type. To suppress formatting for pointers use the -p option, or apply \
1839 the corresponding -r option to suppress formatting for references:" R"(
1841 (lldb) type summary add -p -r --summary-string "${var.ptr}, ${var.value},{${var.byte}}" JustADemo
1843 )" "One-line summaries including all fields in a type can be inferred without supplying an \
1844 explicit summary string by passing the -c option:" R"(
1846 (lldb) type summary add -c JustADemo
1847 (lldb) frame variable demo_instance
1848 (ptr=<address>, value=3.14)
1850 )" "Type summaries normally suppress the nested display of individual fields. To \
1851 supply a summary to supplement the default structure add the -e option:" R"(
1853 (lldb) type summary add -e --summary-string "*ptr = ${*var.ptr}" JustADemo
1855 )" "Now when displaying JustADemo values the int* is displayed, followed by the \
1856 standard LLDB sequence of children, one per line:" R"(
1863 )" "You can also add summaries written in Python. These scripts use lldb public API to \
1864 gather information from your variables and produce a meaningful summary. To start a \
1865 multi-line script use the -P option. The function declaration will be displayed along with \
1866 a comment describing the two arguments. End your script with the word 'DONE' on a line by \
1869 (lldb) type summary add JustADemo -P
1870 def function (valobj,internal_dict):
1871 """valobj: an SBValue which you want to provide a summary for
1872 internal_dict: an LLDB support object not to be used"""
1873 value = valobj.GetChildMemberWithName('value');
1874 return 'My value is ' + value.GetValue();
1877 Alternatively, the -o option can be used when providing a simple one-line Python script:
1879 (lldb) type summary add JustADemo -o "value = valobj.GetChildMemberWithName('value'); return 'My value is ' + value.GetValue();")"
1884 CommandObjectTypeSummaryAdd::DoExecute (Args& command, CommandReturnObject &result)
1886 WarnOnPotentialUnquotedUnsignedType(command, result);
1888 if (m_options.m_is_add_script)
1890 #ifndef LLDB_DISABLE_PYTHON
1891 return Execute_ScriptSummary(command, result);
1893 result.AppendError ("python is disabled");
1894 result.SetStatus(eReturnStatusFailed);
1896 #endif // LLDB_DISABLE_PYTHON
1899 return Execute_StringSummary(command, result);
1903 FixArrayTypeNameWithRegex (ConstString &type_name)
1905 llvm::StringRef type_name_ref(type_name.GetStringRef());
1907 if (type_name_ref.endswith("[]"))
1909 std::string type_name_str(type_name.GetCString());
1910 type_name_str.resize(type_name_str.length()-2);
1911 if (type_name_str.back() != ' ')
1912 type_name_str.append(" \\[[0-9]+\\]");
1914 type_name_str.append("\\[[0-9]+\\]");
1915 type_name.SetCString(type_name_str.c_str());
1922 CommandObjectTypeSummaryAdd::AddSummary(ConstString type_name,
1923 TypeSummaryImplSP entry,
1924 SummaryFormatType type,
1925 std::string category_name,
1928 lldb::TypeCategoryImplSP category;
1929 DataVisualization::Categories::GetCategory(ConstString(category_name.c_str()), category);
1931 if (type == eRegularSummary)
1933 if (FixArrayTypeNameWithRegex (type_name))
1934 type = eRegexSummary;
1937 if (type == eRegexSummary)
1939 RegularExpressionSP typeRX(new RegularExpression());
1940 if (!typeRX->Compile(type_name.GetCString()))
1943 error->SetErrorString("regex format error (maybe this is not really a regex?)");
1947 category->GetRegexTypeSummariesContainer()->Delete(type_name);
1948 category->GetRegexTypeSummariesContainer()->Add(typeRX, entry);
1952 else if (type == eNamedSummary)
1954 // system named summaries do not exist (yet?)
1955 DataVisualization::NamedSummaryFormats::Add(type_name,entry);
1960 category->GetTypeSummariesContainer()->Add(type_name, entry);
1966 CommandObjectTypeSummaryAdd::CommandOptions::g_option_table[] =
1968 { LLDB_OPT_SET_ALL, false, "category", 'w', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeName, "Add this to the given category instead of the default one."},
1969 { LLDB_OPT_SET_ALL, false, "cascade", 'C', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeBoolean, "If true, cascade through typedef chains."},
1970 { LLDB_OPT_SET_ALL, false, "no-value", 'v', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Don't show the value, just show the summary, for this type."},
1971 { LLDB_OPT_SET_ALL, false, "skip-pointers", 'p', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Don't use this format for pointers-to-type objects."},
1972 { LLDB_OPT_SET_ALL, false, "skip-references", 'r', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Don't use this format for references-to-type objects."},
1973 { LLDB_OPT_SET_ALL, false, "regex", 'x', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Type names are actually regular expressions."},
1974 { LLDB_OPT_SET_1 , true, "inline-children", 'c', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "If true, inline all child values into summary string."},
1975 { LLDB_OPT_SET_1 , false, "omit-names", 'O', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "If true, omit value names in the summary display."},
1976 { LLDB_OPT_SET_2 , true, "summary-string", 's', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeSummaryString, "Summary string used to display text and object contents."},
1977 { LLDB_OPT_SET_3, false, "python-script", 'o', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypePythonScript, "Give a one-liner Python script as part of the command."},
1978 { LLDB_OPT_SET_3, false, "python-function", 'F', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypePythonFunction, "Give the name of a Python function to use for this type."},
1979 { LLDB_OPT_SET_3, false, "input-python", 'P', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Input Python code to use for this type manually."},
1980 { LLDB_OPT_SET_2 | LLDB_OPT_SET_3, false, "expand", 'e', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Expand aggregate data types to show children on separate lines."},
1981 { LLDB_OPT_SET_2 | LLDB_OPT_SET_3, false, "hide-empty", 'h', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Do not expand aggregate data types with no children."},
1982 { LLDB_OPT_SET_2 | LLDB_OPT_SET_3, false, "name", 'n', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeName, "A name for this summary string."},
1983 { 0, false, nullptr, 0, 0, nullptr, nullptr, 0, eArgTypeNone, nullptr }
1986 //-------------------------------------------------------------------------
1987 // CommandObjectTypeSummaryDelete
1988 //-------------------------------------------------------------------------
1990 class CommandObjectTypeSummaryDelete : public CommandObjectTypeFormatterDelete
1993 CommandObjectTypeSummaryDelete (CommandInterpreter &interpreter) :
1994 CommandObjectTypeFormatterDelete (interpreter,
1995 eFormatCategoryItemSummary | eFormatCategoryItemRegexSummary,
1996 "type summary delete",
1997 "Delete an existing summary for a type.")
2001 ~CommandObjectTypeSummaryDelete() override = default;
2005 FormatterSpecificDeletion (ConstString typeCS) override
2007 if (m_options.m_language != lldb::eLanguageTypeUnknown)
2009 return DataVisualization::NamedSummaryFormats::Delete(typeCS);
2013 class CommandObjectTypeSummaryClear : public CommandObjectTypeFormatterClear
2016 CommandObjectTypeSummaryClear (CommandInterpreter &interpreter) :
2017 CommandObjectTypeFormatterClear (interpreter,
2018 eFormatCategoryItemSummary | eFormatCategoryItemRegexSummary,
2019 "type summary clear",
2020 "Delete all existing summaries.")
2026 FormatterSpecificDeletion () override
2028 DataVisualization::NamedSummaryFormats::Clear();
2032 //-------------------------------------------------------------------------
2033 // CommandObjectTypeSummaryList
2034 //-------------------------------------------------------------------------
2036 class CommandObjectTypeSummaryList : public CommandObjectTypeFormatterList<TypeSummaryImpl>
2039 CommandObjectTypeSummaryList (CommandInterpreter &interpreter) :
2040 CommandObjectTypeFormatterList(interpreter,
2041 "type summary list",
2042 "Show a list of current summaries.")
2048 FormatterSpecificList (CommandReturnObject &result) override
2050 if (DataVisualization::NamedSummaryFormats::GetCount() > 0)
2052 result.GetOutputStream().Printf("Named summaries:\n");
2053 DataVisualization::NamedSummaryFormats::ForEach( [&result] (ConstString name, const TypeSummaryImplSP& summary_sp) -> bool {
2054 result.GetOutputStream().Printf ("%s: %s\n", name.AsCString(), summary_sp->GetDescription().c_str());
2063 //-------------------------------------------------------------------------
2064 // CommandObjectTypeCategoryDefine
2065 //-------------------------------------------------------------------------
2067 class CommandObjectTypeCategoryDefine : public CommandObjectParsed
2069 class CommandOptions : public Options
2072 CommandOptions (CommandInterpreter &interpreter) :
2073 Options (interpreter),
2074 m_define_enabled(false,false),
2075 m_cate_language(eLanguageTypeUnknown,eLanguageTypeUnknown)
2079 ~CommandOptions() override = default;
2082 SetOptionValue (uint32_t option_idx, const char *option_arg) override
2085 const int short_option = m_getopt_table[option_idx].val;
2087 switch (short_option)
2090 m_define_enabled.SetValueFromString("true");
2093 error = m_cate_language.SetValueFromString(option_arg);
2096 error.SetErrorStringWithFormat ("unrecognized option '%c'", short_option);
2104 OptionParsingStarting () override
2106 m_define_enabled.Clear();
2107 m_cate_language.Clear();
2110 const OptionDefinition*
2111 GetDefinitions () override
2113 return g_option_table;
2116 // Options table: Required for subclasses of Options.
2118 static OptionDefinition g_option_table[];
2120 // Instance variables to hold the values for command options.
2122 OptionValueBoolean m_define_enabled;
2123 OptionValueLanguage m_cate_language;
2126 CommandOptions m_options;
2129 GetOptions () override
2135 CommandObjectTypeCategoryDefine (CommandInterpreter &interpreter) :
2136 CommandObjectParsed(interpreter,
2137 "type category define",
2138 "Define a new category as a source of formatters.",
2140 m_options(interpreter)
2142 CommandArgumentEntry type_arg;
2143 CommandArgumentData type_style_arg;
2145 type_style_arg.arg_type = eArgTypeName;
2146 type_style_arg.arg_repetition = eArgRepeatPlus;
2148 type_arg.push_back (type_style_arg);
2150 m_arguments.push_back (type_arg);
2153 ~CommandObjectTypeCategoryDefine() override = default;
2157 DoExecute (Args& command, CommandReturnObject &result) override
2159 const size_t argc = command.GetArgumentCount();
2163 result.AppendErrorWithFormat ("%s takes 1 or more args.\n", m_cmd_name.c_str());
2164 result.SetStatus(eReturnStatusFailed);
2168 for (size_t i = 0; i < argc; i++)
2170 const char* cateName = command.GetArgumentAtIndex(i);
2171 TypeCategoryImplSP category_sp;
2172 if (DataVisualization::Categories::GetCategory(ConstString(cateName), category_sp) && category_sp)
2174 category_sp->AddLanguage(m_options.m_cate_language.GetCurrentValue());
2175 if (m_options.m_define_enabled.GetCurrentValue())
2176 DataVisualization::Categories::Enable(category_sp, TypeCategoryMap::Default);
2180 result.SetStatus(eReturnStatusSuccessFinishResult);
2181 return result.Succeeded();
2186 CommandObjectTypeCategoryDefine::CommandOptions::g_option_table[] =
2188 { LLDB_OPT_SET_ALL, false, "enabled", 'e', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "If specified, this category will be created enabled."},
2189 { LLDB_OPT_SET_ALL, false, "language", 'l', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeLanguage, "Specify the language that this category is supported for."},
2190 { 0, false, nullptr, 0, 0, nullptr, nullptr, 0, eArgTypeNone, nullptr }
2193 //-------------------------------------------------------------------------
2194 // CommandObjectTypeCategoryEnable
2195 //-------------------------------------------------------------------------
2197 class CommandObjectTypeCategoryEnable : public CommandObjectParsed
2199 class CommandOptions : public Options
2202 CommandOptions (CommandInterpreter &interpreter) :
2203 Options (interpreter)
2207 ~CommandOptions() override = default;
2210 SetOptionValue (uint32_t option_idx, const char *option_arg) override
2213 const int short_option = m_getopt_table[option_idx].val;
2215 switch (short_option)
2220 m_language = Language::GetLanguageTypeFromString(option_arg);
2221 if (m_language == lldb::eLanguageTypeUnknown)
2222 error.SetErrorStringWithFormat ("unrecognized language '%s'", option_arg);
2226 error.SetErrorStringWithFormat ("unrecognized option '%c'", short_option);
2234 OptionParsingStarting () override
2236 m_language = lldb::eLanguageTypeUnknown;
2239 const OptionDefinition*
2240 GetDefinitions () override
2242 return g_option_table;
2245 // Options table: Required for subclasses of Options.
2247 static OptionDefinition g_option_table[];
2249 // Instance variables to hold the values for command options.
2251 lldb::LanguageType m_language;
2255 CommandOptions m_options;
2258 GetOptions () override
2264 CommandObjectTypeCategoryEnable (CommandInterpreter &interpreter) :
2265 CommandObjectParsed(interpreter,
2266 "type category enable",
2267 "Enable a category as a source of formatters.",
2269 m_options(interpreter)
2271 CommandArgumentEntry type_arg;
2272 CommandArgumentData type_style_arg;
2274 type_style_arg.arg_type = eArgTypeName;
2275 type_style_arg.arg_repetition = eArgRepeatPlus;
2277 type_arg.push_back (type_style_arg);
2279 m_arguments.push_back (type_arg);
2283 ~CommandObjectTypeCategoryEnable() override = default;
2287 DoExecute (Args& command, CommandReturnObject &result) override
2289 const size_t argc = command.GetArgumentCount();
2292 m_options.m_language == lldb::eLanguageTypeUnknown)
2294 result.AppendErrorWithFormat ("%s takes arguments and/or a language", m_cmd_name.c_str());
2295 result.SetStatus(eReturnStatusFailed);
2299 if (argc == 1 && strcmp(command.GetArgumentAtIndex(0),"*") == 0)
2301 DataVisualization::Categories::EnableStar();
2305 for (int i = argc - 1; i >= 0; i--)
2307 const char* typeA = command.GetArgumentAtIndex(i);
2308 ConstString typeCS(typeA);
2312 result.AppendError("empty category name not allowed");
2313 result.SetStatus(eReturnStatusFailed);
2316 DataVisualization::Categories::Enable(typeCS);
2317 lldb::TypeCategoryImplSP cate;
2318 if (DataVisualization::Categories::GetCategory(typeCS, cate) && cate)
2320 if (cate->GetCount() == 0)
2322 result.AppendWarning("empty category enabled (typo?)");
2328 if (m_options.m_language != lldb::eLanguageTypeUnknown)
2329 DataVisualization::Categories::Enable(m_options.m_language);
2331 result.SetStatus(eReturnStatusSuccessFinishResult);
2332 return result.Succeeded();
2337 CommandObjectTypeCategoryEnable::CommandOptions::g_option_table[] =
2339 { LLDB_OPT_SET_ALL, false, "language", 'l', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeLanguage, "Enable the category for this language."},
2340 { 0, false, nullptr, 0, 0, nullptr, nullptr, 0, eArgTypeNone, nullptr }
2343 //-------------------------------------------------------------------------
2344 // CommandObjectTypeCategoryDelete
2345 //-------------------------------------------------------------------------
2347 class CommandObjectTypeCategoryDelete : public CommandObjectParsed
2350 CommandObjectTypeCategoryDelete (CommandInterpreter &interpreter) :
2351 CommandObjectParsed(interpreter,
2352 "type category delete",
2353 "Delete a category and all associated formatters.",
2356 CommandArgumentEntry type_arg;
2357 CommandArgumentData type_style_arg;
2359 type_style_arg.arg_type = eArgTypeName;
2360 type_style_arg.arg_repetition = eArgRepeatPlus;
2362 type_arg.push_back (type_style_arg);
2364 m_arguments.push_back (type_arg);
2367 ~CommandObjectTypeCategoryDelete() override = default;
2371 DoExecute (Args& command, CommandReturnObject &result) override
2373 const size_t argc = command.GetArgumentCount();
2377 result.AppendErrorWithFormat ("%s takes 1 or more arg.\n", m_cmd_name.c_str());
2378 result.SetStatus(eReturnStatusFailed);
2382 bool success = true;
2384 // the order is not relevant here
2385 for (int i = argc - 1; i >= 0; i--)
2387 const char* typeA = command.GetArgumentAtIndex(i);
2388 ConstString typeCS(typeA);
2392 result.AppendError("empty category name not allowed");
2393 result.SetStatus(eReturnStatusFailed);
2396 if (!DataVisualization::Categories::Delete(typeCS))
2397 success = false; // keep deleting even if we hit an error
2401 result.SetStatus(eReturnStatusSuccessFinishResult);
2402 return result.Succeeded();
2406 result.AppendError("cannot delete one or more categories\n");
2407 result.SetStatus(eReturnStatusFailed);
2413 //-------------------------------------------------------------------------
2414 // CommandObjectTypeCategoryDisable
2415 //-------------------------------------------------------------------------
2417 class CommandObjectTypeCategoryDisable : public CommandObjectParsed
2419 class CommandOptions : public Options
2422 CommandOptions (CommandInterpreter &interpreter) :
2423 Options (interpreter)
2427 ~CommandOptions() override = default;
2430 SetOptionValue (uint32_t option_idx, const char *option_arg) override
2433 const int short_option = m_getopt_table[option_idx].val;
2435 switch (short_option)
2440 m_language = Language::GetLanguageTypeFromString(option_arg);
2441 if (m_language == lldb::eLanguageTypeUnknown)
2442 error.SetErrorStringWithFormat ("unrecognized language '%s'", option_arg);
2446 error.SetErrorStringWithFormat ("unrecognized option '%c'", short_option);
2454 OptionParsingStarting () override
2456 m_language = lldb::eLanguageTypeUnknown;
2459 const OptionDefinition*
2460 GetDefinitions () override
2462 return g_option_table;
2465 // Options table: Required for subclasses of Options.
2467 static OptionDefinition g_option_table[];
2469 // Instance variables to hold the values for command options.
2471 lldb::LanguageType m_language;
2474 CommandOptions m_options;
2477 GetOptions () override
2483 CommandObjectTypeCategoryDisable (CommandInterpreter &interpreter) :
2484 CommandObjectParsed(interpreter,
2485 "type category disable",
2486 "Disable a category as a source of formatters.",
2488 m_options(interpreter)
2490 CommandArgumentEntry type_arg;
2491 CommandArgumentData type_style_arg;
2493 type_style_arg.arg_type = eArgTypeName;
2494 type_style_arg.arg_repetition = eArgRepeatPlus;
2496 type_arg.push_back (type_style_arg);
2498 m_arguments.push_back (type_arg);
2501 ~CommandObjectTypeCategoryDisable() override = default;
2505 DoExecute (Args& command, CommandReturnObject &result) override
2507 const size_t argc = command.GetArgumentCount();
2510 m_options.m_language == lldb::eLanguageTypeUnknown)
2512 result.AppendErrorWithFormat ("%s takes arguments and/or a language", m_cmd_name.c_str());
2513 result.SetStatus(eReturnStatusFailed);
2517 if (argc == 1 && strcmp(command.GetArgumentAtIndex(0),"*") == 0)
2519 DataVisualization::Categories::DisableStar();
2523 // the order is not relevant here
2524 for (int i = argc - 1; i >= 0; i--)
2526 const char* typeA = command.GetArgumentAtIndex(i);
2527 ConstString typeCS(typeA);
2531 result.AppendError("empty category name not allowed");
2532 result.SetStatus(eReturnStatusFailed);
2535 DataVisualization::Categories::Disable(typeCS);
2539 if (m_options.m_language != lldb::eLanguageTypeUnknown)
2540 DataVisualization::Categories::Disable(m_options.m_language);
2542 result.SetStatus(eReturnStatusSuccessFinishResult);
2543 return result.Succeeded();
2548 CommandObjectTypeCategoryDisable::CommandOptions::g_option_table[] =
2550 { LLDB_OPT_SET_ALL, false, "language", 'l', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeLanguage, "Enable the category for this language."},
2551 { 0, false, nullptr, 0, 0, nullptr, nullptr, 0, eArgTypeNone, nullptr }
2554 //-------------------------------------------------------------------------
2555 // CommandObjectTypeCategoryList
2556 //-------------------------------------------------------------------------
2558 class CommandObjectTypeCategoryList : public CommandObjectParsed
2561 CommandObjectTypeCategoryList (CommandInterpreter &interpreter) :
2562 CommandObjectParsed(interpreter,
2563 "type category list",
2564 "Provide a list of all existing categories.",
2567 CommandArgumentEntry type_arg;
2568 CommandArgumentData type_style_arg;
2570 type_style_arg.arg_type = eArgTypeName;
2571 type_style_arg.arg_repetition = eArgRepeatOptional;
2573 type_arg.push_back (type_style_arg);
2575 m_arguments.push_back (type_arg);
2578 ~CommandObjectTypeCategoryList() override = default;
2582 DoExecute (Args& command, CommandReturnObject &result) override
2584 const size_t argc = command.GetArgumentCount();
2586 std::unique_ptr<RegularExpression> regex;
2590 regex.reset(new RegularExpression());
2591 const char* arg = command.GetArgumentAtIndex(0);
2592 if (!regex->Compile(arg))
2594 result.AppendErrorWithFormat("syntax error in category regular expression '%s'", arg);
2595 result.SetStatus(eReturnStatusFailed);
2601 result.AppendErrorWithFormat ("%s takes 0 or one arg.\n", m_cmd_name.c_str());
2602 result.SetStatus(eReturnStatusFailed);
2606 DataVisualization::Categories::ForEach( [®ex, &result] (const lldb::TypeCategoryImplSP& category_sp) -> bool {
2610 if (0 == strcmp(category_sp->GetName(), regex->GetText()))
2614 else if (regex->Execute(category_sp->GetName()))
2623 result.GetOutputStream().Printf("Category: %s\n", category_sp->GetDescription().c_str());
2628 result.SetStatus(eReturnStatusSuccessFinishResult);
2629 return result.Succeeded();
2633 //-------------------------------------------------------------------------
2634 // CommandObjectTypeFilterList
2635 //-------------------------------------------------------------------------
2637 class CommandObjectTypeFilterList : public CommandObjectTypeFormatterList<TypeFilterImpl>
2640 CommandObjectTypeFilterList (CommandInterpreter &interpreter) :
2641 CommandObjectTypeFormatterList(interpreter,
2643 "Show a list of current filters.")
2648 #ifndef LLDB_DISABLE_PYTHON
2650 //-------------------------------------------------------------------------
2651 // CommandObjectTypeSynthList
2652 //-------------------------------------------------------------------------
2654 class CommandObjectTypeSynthList : public CommandObjectTypeFormatterList<SyntheticChildren>
2657 CommandObjectTypeSynthList (CommandInterpreter &interpreter) :
2658 CommandObjectTypeFormatterList(interpreter,
2659 "type synthetic list",
2660 "Show a list of current synthetic providers.")
2665 #endif // LLDB_DISABLE_PYTHON
2667 //-------------------------------------------------------------------------
2668 // CommandObjectTypeFilterDelete
2669 //-------------------------------------------------------------------------
2671 class CommandObjectTypeFilterDelete : public CommandObjectTypeFormatterDelete
2674 CommandObjectTypeFilterDelete (CommandInterpreter &interpreter) :
2675 CommandObjectTypeFormatterDelete (interpreter,
2676 eFormatCategoryItemFilter | eFormatCategoryItemRegexFilter,
2677 "type filter delete",
2678 "Delete an existing filter for a type.")
2682 ~CommandObjectTypeFilterDelete() override = default;
2685 #ifndef LLDB_DISABLE_PYTHON
2687 //-------------------------------------------------------------------------
2688 // CommandObjectTypeSynthDelete
2689 //-------------------------------------------------------------------------
2691 class CommandObjectTypeSynthDelete : public CommandObjectTypeFormatterDelete
2694 CommandObjectTypeSynthDelete (CommandInterpreter &interpreter) :
2695 CommandObjectTypeFormatterDelete (interpreter,
2696 eFormatCategoryItemSynth | eFormatCategoryItemRegexSynth,
2697 "type synthetic delete",
2698 "Delete an existing synthetic provider for a type.")
2702 ~CommandObjectTypeSynthDelete() override = default;
2705 #endif // LLDB_DISABLE_PYTHON
2707 //-------------------------------------------------------------------------
2708 // CommandObjectTypeFilterClear
2709 //-------------------------------------------------------------------------
2711 class CommandObjectTypeFilterClear : public CommandObjectTypeFormatterClear
2714 CommandObjectTypeFilterClear (CommandInterpreter &interpreter) :
2715 CommandObjectTypeFormatterClear (interpreter,
2716 eFormatCategoryItemFilter | eFormatCategoryItemRegexFilter,
2717 "type filter clear",
2718 "Delete all existing filter.")
2723 #ifndef LLDB_DISABLE_PYTHON
2724 //-------------------------------------------------------------------------
2725 // CommandObjectTypeSynthClear
2726 //-------------------------------------------------------------------------
2728 class CommandObjectTypeSynthClear : public CommandObjectTypeFormatterClear
2731 CommandObjectTypeSynthClear (CommandInterpreter &interpreter) :
2732 CommandObjectTypeFormatterClear (interpreter,
2733 eFormatCategoryItemSynth | eFormatCategoryItemRegexSynth,
2734 "type synthetic clear",
2735 "Delete all existing synthetic providers.")
2741 CommandObjectTypeSynthAdd::Execute_HandwritePython (Args& command, CommandReturnObject &result)
2743 SynthAddOptions *options = new SynthAddOptions ( m_options.m_skip_pointers,
2744 m_options.m_skip_references,
2745 m_options.m_cascade,
2747 m_options.m_category);
2749 const size_t argc = command.GetArgumentCount();
2751 for (size_t i = 0; i < argc; i++)
2753 const char* typeA = command.GetArgumentAtIndex(i);
2754 if (typeA && *typeA)
2755 options->m_target_types << typeA;
2758 result.AppendError("empty typenames not allowed");
2759 result.SetStatus(eReturnStatusFailed);
2764 m_interpreter.GetPythonCommandsFromIOHandler (" ", // Prompt
2765 *this, // IOHandlerDelegate
2766 true, // Run IOHandler in async mode
2767 options); // Baton for the "io_handler" that will be passed back into our IOHandlerDelegate functions
2768 result.SetStatus(eReturnStatusSuccessFinishNoResult);
2769 return result.Succeeded();
2773 CommandObjectTypeSynthAdd::Execute_PythonClass (Args& command, CommandReturnObject &result)
2775 const size_t argc = command.GetArgumentCount();
2779 result.AppendErrorWithFormat ("%s takes one or more args.\n", m_cmd_name.c_str());
2780 result.SetStatus(eReturnStatusFailed);
2784 if (m_options.m_class_name.empty() && !m_options.m_input_python)
2786 result.AppendErrorWithFormat ("%s needs either a Python class name or -P to directly input Python code.\n", m_cmd_name.c_str());
2787 result.SetStatus(eReturnStatusFailed);
2791 SyntheticChildrenSP entry;
2793 ScriptedSyntheticChildren* impl = new ScriptedSyntheticChildren(SyntheticChildren::Flags().
2794 SetCascades(m_options.m_cascade).
2795 SetSkipPointers(m_options.m_skip_pointers).
2796 SetSkipReferences(m_options.m_skip_references),
2797 m_options.m_class_name.c_str());
2801 ScriptInterpreter *interpreter = m_interpreter.GetScriptInterpreter();
2803 if (interpreter && !interpreter->CheckObjectExists(impl->GetPythonClassName()))
2804 result.AppendWarning("The provided class does not exist - please define it before attempting to use this synthetic provider");
2806 // now I have a valid provider, let's add it to every type
2808 lldb::TypeCategoryImplSP category;
2809 DataVisualization::Categories::GetCategory(ConstString(m_options.m_category.c_str()), category);
2813 for (size_t i = 0; i < argc; i++)
2815 const char* typeA = command.GetArgumentAtIndex(i);
2816 ConstString typeCS(typeA);
2819 if (!AddSynth(typeCS,
2821 m_options.m_regex ? eRegexSynth : eRegularSynth,
2822 m_options.m_category,
2825 result.AppendError(error.AsCString());
2826 result.SetStatus(eReturnStatusFailed);
2832 result.AppendError("empty typenames not allowed");
2833 result.SetStatus(eReturnStatusFailed);
2838 result.SetStatus(eReturnStatusSuccessFinishNoResult);
2839 return result.Succeeded();
2842 CommandObjectTypeSynthAdd::CommandObjectTypeSynthAdd (CommandInterpreter &interpreter) :
2843 CommandObjectParsed(interpreter,
2844 "type synthetic add",
2845 "Add a new synthetic provider for a type.",
2847 IOHandlerDelegateMultiline ("DONE"),
2848 m_options (interpreter)
2850 CommandArgumentEntry type_arg;
2851 CommandArgumentData type_style_arg;
2853 type_style_arg.arg_type = eArgTypeName;
2854 type_style_arg.arg_repetition = eArgRepeatPlus;
2856 type_arg.push_back (type_style_arg);
2858 m_arguments.push_back (type_arg);
2862 CommandObjectTypeSynthAdd::AddSynth(ConstString type_name,
2863 SyntheticChildrenSP entry,
2864 SynthFormatType type,
2865 std::string category_name,
2868 lldb::TypeCategoryImplSP category;
2869 DataVisualization::Categories::GetCategory(ConstString(category_name.c_str()), category);
2871 if (type == eRegularSynth)
2873 if (FixArrayTypeNameWithRegex (type_name))
2877 if (category->AnyMatches(type_name,
2878 eFormatCategoryItemFilter | eFormatCategoryItemRegexFilter,
2882 error->SetErrorStringWithFormat("cannot add synthetic for type %s when filter is defined in same category!", type_name.AsCString());
2886 if (type == eRegexSynth)
2888 RegularExpressionSP typeRX(new RegularExpression());
2889 if (!typeRX->Compile(type_name.GetCString()))
2892 error->SetErrorString("regex format error (maybe this is not really a regex?)");
2896 category->GetRegexTypeSyntheticsContainer()->Delete(type_name);
2897 category->GetRegexTypeSyntheticsContainer()->Add(typeRX, entry);
2903 category->GetTypeSyntheticsContainer()->Add(type_name, entry);
2909 CommandObjectTypeSynthAdd::CommandOptions::g_option_table[] =
2911 { LLDB_OPT_SET_ALL, false, "cascade", 'C', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeBoolean, "If true, cascade through typedef chains."},
2912 { LLDB_OPT_SET_ALL, false, "skip-pointers", 'p', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Don't use this format for pointers-to-type objects."},
2913 { LLDB_OPT_SET_ALL, false, "skip-references", 'r', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Don't use this format for references-to-type objects."},
2914 { LLDB_OPT_SET_ALL, false, "category", 'w', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeName, "Add this to the given category instead of the default one."},
2915 { LLDB_OPT_SET_2, false, "python-class", 'l', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypePythonClass, "Use this Python class to produce synthetic children."},
2916 { LLDB_OPT_SET_3, false, "input-python", 'P', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Type Python code to generate a class that provides synthetic children."},
2917 { LLDB_OPT_SET_ALL, false, "regex", 'x', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Type names are actually regular expressions."},
2918 { 0, false, nullptr, 0, 0, nullptr, nullptr, 0, eArgTypeNone, nullptr }
2921 #endif // LLDB_DISABLE_PYTHON
2923 class CommandObjectTypeFilterAdd : public CommandObjectParsed
2926 class CommandOptions : public Options
2928 typedef std::vector<std::string> option_vector;
2931 CommandOptions (CommandInterpreter &interpreter) :
2932 Options (interpreter)
2936 ~CommandOptions() override = default;
2939 SetOptionValue (uint32_t option_idx, const char *option_arg) override
2942 const int short_option = m_getopt_table[option_idx].val;
2945 switch (short_option)
2948 m_cascade = Args::StringToBoolean(option_arg, true, &success);
2950 error.SetErrorStringWithFormat("invalid value for cascade: %s", option_arg);
2953 m_expr_paths.push_back(option_arg);
2954 has_child_list = true;
2957 m_skip_pointers = true;
2960 m_skip_references = true;
2963 m_category = std::string(option_arg);
2969 error.SetErrorStringWithFormat ("unrecognized option '%c'", short_option);
2977 OptionParsingStarting () override
2980 m_skip_pointers = false;
2981 m_skip_references = false;
2982 m_category = "default";
2983 m_expr_paths.clear();
2984 has_child_list = false;
2988 const OptionDefinition*
2989 GetDefinitions () override
2991 return g_option_table;
2994 // Options table: Required for subclasses of Options.
2996 static OptionDefinition g_option_table[];
2998 // Instance variables to hold the values for command options.
3001 bool m_skip_references;
3002 bool m_skip_pointers;
3003 bool m_input_python;
3004 option_vector m_expr_paths;
3005 std::string m_category;
3006 bool has_child_list;
3009 typedef option_vector::iterator ExpressionPathsIterator;
3012 CommandOptions m_options;
3015 GetOptions () override
3020 enum FilterFormatType
3027 AddFilter(ConstString type_name,
3028 TypeFilterImplSP entry,
3029 FilterFormatType type,
3030 std::string category_name,
3033 lldb::TypeCategoryImplSP category;
3034 DataVisualization::Categories::GetCategory(ConstString(category_name.c_str()), category);
3036 if (type == eRegularFilter)
3038 if (FixArrayTypeNameWithRegex (type_name))
3039 type = eRegexFilter;
3042 if (category->AnyMatches(type_name,
3043 eFormatCategoryItemSynth | eFormatCategoryItemRegexSynth,
3047 error->SetErrorStringWithFormat("cannot add filter for type %s when synthetic is defined in same category!", type_name.AsCString());
3051 if (type == eRegexFilter)
3053 RegularExpressionSP typeRX(new RegularExpression());
3054 if (!typeRX->Compile(type_name.GetCString()))
3057 error->SetErrorString("regex format error (maybe this is not really a regex?)");
3061 category->GetRegexTypeFiltersContainer()->Delete(type_name);
3062 category->GetRegexTypeFiltersContainer()->Add(typeRX, entry);
3068 category->GetTypeFiltersContainer()->Add(type_name, entry);
3074 CommandObjectTypeFilterAdd (CommandInterpreter &interpreter) :
3075 CommandObjectParsed(interpreter,
3077 "Add a new filter for a type.",
3079 m_options (interpreter)
3081 CommandArgumentEntry type_arg;
3082 CommandArgumentData type_style_arg;
3084 type_style_arg.arg_type = eArgTypeName;
3085 type_style_arg.arg_repetition = eArgRepeatPlus;
3087 type_arg.push_back (type_style_arg);
3089 m_arguments.push_back (type_arg);
3093 The following examples of 'type filter add' refer to this code snippet for context:
3108 Adding a simple filter:
3110 (lldb) type filter add --child a --child g Foo
3111 (lldb) frame variable my_foo
3113 )" "Produces output where only a and g are displayed. Other children of my_foo \
3114 (b, c, d, e, f, h and i) are available by asking for them explicitly:" R"(
3116 (lldb) frame variable my_foo.b my_foo.c my_foo.i
3118 )" "The formatting option --raw on frame variable bypasses the filter, showing \
3119 all children of my_foo as if no filter was defined:" R"(
3121 (lldb) frame variable my_foo --raw)"
3125 ~CommandObjectTypeFilterAdd() override = default;
3129 DoExecute (Args& command, CommandReturnObject &result) override
3131 const size_t argc = command.GetArgumentCount();
3135 result.AppendErrorWithFormat ("%s takes one or more args.\n", m_cmd_name.c_str());
3136 result.SetStatus(eReturnStatusFailed);
3140 if (m_options.m_expr_paths.empty())
3142 result.AppendErrorWithFormat ("%s needs one or more children.\n", m_cmd_name.c_str());
3143 result.SetStatus(eReturnStatusFailed);
3147 TypeFilterImplSP entry(new TypeFilterImpl(SyntheticChildren::Flags().SetCascades(m_options.m_cascade).
3148 SetSkipPointers(m_options.m_skip_pointers).
3149 SetSkipReferences(m_options.m_skip_references)));
3151 // go through the expression paths
3152 CommandOptions::ExpressionPathsIterator begin, end = m_options.m_expr_paths.end();
3154 for (begin = m_options.m_expr_paths.begin(); begin != end; begin++)
3155 entry->AddExpressionPath(*begin);
3158 // now I have a valid provider, let's add it to every type
3160 lldb::TypeCategoryImplSP category;
3161 DataVisualization::Categories::GetCategory(ConstString(m_options.m_category.c_str()), category);
3165 WarnOnPotentialUnquotedUnsignedType(command, result);
3167 for (size_t i = 0; i < argc; i++)
3169 const char* typeA = command.GetArgumentAtIndex(i);
3170 ConstString typeCS(typeA);
3173 if (!AddFilter(typeCS,
3175 m_options.m_regex ? eRegexFilter : eRegularFilter,
3176 m_options.m_category,
3179 result.AppendError(error.AsCString());
3180 result.SetStatus(eReturnStatusFailed);
3186 result.AppendError("empty typenames not allowed");
3187 result.SetStatus(eReturnStatusFailed);
3192 result.SetStatus(eReturnStatusSuccessFinishNoResult);
3193 return result.Succeeded();
3198 CommandObjectTypeFilterAdd::CommandOptions::g_option_table[] =
3200 { LLDB_OPT_SET_ALL, false, "cascade", 'C', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeBoolean, "If true, cascade through typedef chains."},
3201 { LLDB_OPT_SET_ALL, false, "skip-pointers", 'p', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Don't use this format for pointers-to-type objects."},
3202 { LLDB_OPT_SET_ALL, false, "skip-references", 'r', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Don't use this format for references-to-type objects."},
3203 { LLDB_OPT_SET_ALL, false, "category", 'w', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeName, "Add this to the given category instead of the default one."},
3204 { LLDB_OPT_SET_ALL, false, "child", 'c', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeExpressionPath, "Include this expression path in the synthetic view."},
3205 { LLDB_OPT_SET_ALL, false, "regex", 'x', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Type names are actually regular expressions."},
3206 { 0, false, nullptr, 0, 0, nullptr, nullptr, 0, eArgTypeNone, nullptr }
3209 //----------------------------------------------------------------------
3211 //----------------------------------------------------------------------
3212 class CommandObjectTypeLookup : public CommandObjectRaw
3215 // this function is allowed to do a more aggressive job at guessing languages than the expression parser
3216 // is comfortable with - so leave the original call alone and add one that is specific to type lookup
3218 GuessLanguage (StackFrame *frame)
3220 lldb::LanguageType lang_type = lldb::eLanguageTypeUnknown;
3225 lang_type = frame->GuessLanguage();
3226 if (lang_type != lldb::eLanguageTypeUnknown)
3229 Symbol *s = frame->GetSymbolContext(eSymbolContextSymbol).symbol;
3231 lang_type = s->GetMangled().GuessLanguage();
3236 class CommandOptions : public OptionGroup
3242 m_language(eLanguageTypeUnknown)
3245 ~CommandOptions() override = default;
3248 GetNumDefinitions () override
3253 const OptionDefinition*
3254 GetDefinitions () override
3256 return g_option_table;
3260 SetOptionValue (CommandInterpreter &interpreter,
3261 uint32_t option_idx,
3262 const char *option_value) override
3266 const int short_option = g_option_table[option_idx].short_option;
3268 switch (short_option)
3275 m_language = Language::GetLanguageTypeFromString(option_value);
3279 error.SetErrorStringWithFormat("invalid short option character '%c'", short_option);
3287 OptionParsingStarting (CommandInterpreter &interpreter) override
3289 m_show_help = false;
3290 m_language = eLanguageTypeUnknown;
3293 // Options table: Required for subclasses of Options.
3295 static OptionDefinition g_option_table[];
3297 lldb::LanguageType m_language;
3300 OptionGroupOptions m_option_group;
3301 CommandOptions m_command_options;
3304 CommandObjectTypeLookup (CommandInterpreter &interpreter) :
3305 CommandObjectRaw (interpreter,
3307 "Lookup types and declarations in the current target, following language-specific naming conventions.",
3308 "type lookup <type-specifier>",
3309 eCommandRequiresTarget),
3310 m_option_group(interpreter),
3313 m_option_group.Append(&m_command_options);
3314 m_option_group.Finalize();
3317 ~CommandObjectTypeLookup() override = default;
3320 GetOptions () override
3322 return &m_option_group;
3326 GetHelpLong () override
3328 if (m_cmd_help_long.empty())
3330 StreamString stream;
3331 // FIXME: hardcoding languages is not good
3332 lldb::LanguageType languages[] = {eLanguageTypeObjC,eLanguageTypeC_plus_plus};
3334 for(const auto lang_type : languages)
3336 if (auto language = Language::FindPlugin(lang_type))
3338 if (const char* help = language->GetLanguageSpecificTypeLookupHelp())
3340 stream.Printf("%s\n", help);
3345 if (stream.GetData())
3346 m_cmd_help_long.assign(stream.GetString());
3348 return this->CommandObject::GetHelpLong();
3352 DoExecute (const char *raw_command_line, CommandReturnObject &result) override
3354 if (!raw_command_line || !raw_command_line[0])
3356 result.SetError("type lookup cannot be invoked without a type name as argument");
3360 m_option_group.NotifyOptionParsingStarting();
3362 const char * name_of_type = nullptr;
3364 if (raw_command_line[0] == '-')
3366 // We have some options and these options MUST end with --.
3367 const char *end_options = nullptr;
3368 const char *s = raw_command_line;
3371 end_options = ::strstr (s, "--");
3374 end_options += 2; // Get past the "--"
3375 if (::isspace (end_options[0]))
3377 name_of_type = end_options;
3378 while (::isspace (*name_of_type))
3388 Args args (llvm::StringRef(raw_command_line, end_options - raw_command_line));
3389 if (!ParseOptions (args, result))
3392 Error error (m_option_group.NotifyOptionParsingFinished());
3395 result.AppendError (error.AsCString());
3396 result.SetStatus (eReturnStatusFailed);
3401 if (nullptr == name_of_type)
3402 name_of_type = raw_command_line;
3404 TargetSP target_sp(GetCommandInterpreter().GetDebugger().GetSelectedTarget());
3405 const bool fill_all_in = true;
3406 ExecutionContext exe_ctx(target_sp.get(), fill_all_in);
3407 ExecutionContextScope *best_scope = exe_ctx.GetBestExecutionContextScope();
3409 bool any_found = false;
3411 std::vector<Language*> languages;
3413 bool is_global_search = false;
3415 if ( (is_global_search = (m_command_options.m_language == eLanguageTypeUnknown)) )
3417 // FIXME: hardcoding languages is not good
3418 languages.push_back(Language::FindPlugin(eLanguageTypeObjC));
3419 languages.push_back(Language::FindPlugin(eLanguageTypeC_plus_plus));
3423 languages.push_back(Language::FindPlugin(m_command_options.m_language));
3426 // This is not the most efficient way to do this, but we support very few languages
3427 // so the cost of the sort is going to be dwarfed by the actual lookup anyway
3428 if (StackFrame* frame = m_exe_ctx.GetFramePtr())
3430 LanguageType lang = GuessLanguage(frame);
3431 if (lang != eLanguageTypeUnknown)
3433 std::sort(languages.begin(),
3435 [lang] (Language* lang1,
3436 Language* lang2) -> bool {
3437 if (!lang1 || !lang2) return false;
3438 LanguageType lt1 = lang1->GetLanguageType();
3439 LanguageType lt2 = lang2->GetLanguageType();
3440 if (lt1 == lang) return true; // make the selected frame's language come first
3441 if (lt2 == lang) return false; // make the selected frame's language come first
3442 return (lt1 < lt2); // normal comparison otherwise
3447 for (Language* language : languages)
3452 if (auto scavenger = language->GetTypeScavenger())
3454 Language::TypeScavenger::ResultSet search_results;
3455 if (scavenger->Find(best_scope, name_of_type, search_results) > 0)
3457 for (const auto& search_result : search_results)
3459 if (search_result && search_result->IsValid())
3462 search_result->DumpToStream(result.GetOutputStream(), this->m_command_options.m_show_help);
3466 // this is "type lookup SomeName" and we did find a match, so get out
3467 if (any_found && is_global_search)
3473 result.AppendMessageWithFormat("no type was found matching '%s'\n", name_of_type);
3475 result.SetStatus (any_found ? lldb::eReturnStatusSuccessFinishResult : lldb::eReturnStatusSuccessFinishNoResult);
3481 CommandObjectTypeLookup::CommandOptions::g_option_table[] =
3483 { LLDB_OPT_SET_ALL, false, "show-help", 'h', OptionParser::eNoArgument, nullptr, nullptr, 0, eArgTypeNone, "Display available help for types"},
3484 { LLDB_OPT_SET_ALL, false, "language", 'l', OptionParser::eRequiredArgument, nullptr, nullptr, 0, eArgTypeLanguage, "Which language's types should the search scope be"},
3485 { 0, false, nullptr, 0, 0, nullptr, nullptr, 0, eArgTypeNone, nullptr }
3488 template <typename FormatterType>
3489 class CommandObjectFormatterInfo : public CommandObjectRaw
3492 typedef std::function<typename FormatterType::SharedPointer(ValueObject&)> DiscoveryFunction;
3493 CommandObjectFormatterInfo (CommandInterpreter &interpreter,
3494 const char* formatter_name,
3495 DiscoveryFunction discovery_func) :
3496 CommandObjectRaw(interpreter,
3500 eCommandRequiresFrame),
3501 m_formatter_name(formatter_name ? formatter_name : ""),
3502 m_discovery_function(discovery_func)
3505 name.Printf("type %s info", formatter_name);
3506 SetCommandName(name.GetData());
3508 help.Printf("This command evaluates the provided expression and shows which %s is applied to the resulting value (if any).", formatter_name);
3509 SetHelp(help.GetData());
3510 StreamString syntax;
3511 syntax.Printf("type %s info <expr>", formatter_name);
3512 SetSyntax(syntax.GetData());
3515 ~CommandObjectFormatterInfo() override = default;
3519 DoExecute (const char *command, CommandReturnObject &result) override
3521 TargetSP target_sp = m_interpreter.GetDebugger().GetSelectedTarget();
3522 Thread *thread = GetDefaultThread();
3525 result.AppendError("no default thread");
3526 result.SetStatus(lldb::eReturnStatusFailed);
3530 StackFrameSP frame_sp = thread->GetSelectedFrame();
3531 ValueObjectSP result_valobj_sp;
3532 EvaluateExpressionOptions options;
3533 lldb::ExpressionResults expr_result = target_sp->EvaluateExpression(command, frame_sp.get(), result_valobj_sp, options);
3534 if (expr_result == eExpressionCompleted && result_valobj_sp)
3536 result_valobj_sp = result_valobj_sp->GetQualifiedRepresentationIfAvailable(target_sp->GetPreferDynamicValue(), target_sp->GetEnableSyntheticValue());
3537 typename FormatterType::SharedPointer formatter_sp = m_discovery_function(*result_valobj_sp);
3540 std::string description(formatter_sp->GetDescription());
3541 result.AppendMessageWithFormat("%s applied to (%s) %s is: %s\n",
3542 m_formatter_name.c_str(),
3543 result_valobj_sp->GetDisplayTypeName().AsCString("<unknown>"),
3545 description.c_str());
3546 result.SetStatus(lldb::eReturnStatusSuccessFinishResult);
3550 result.AppendMessageWithFormat("no %s applies to (%s) %s\n",
3551 m_formatter_name.c_str(),
3552 result_valobj_sp->GetDisplayTypeName().AsCString("<unknown>"),
3554 result.SetStatus(lldb::eReturnStatusSuccessFinishNoResult);
3560 result.AppendError("failed to evaluate expression");
3561 result.SetStatus(lldb::eReturnStatusFailed);
3567 std::string m_formatter_name;
3568 DiscoveryFunction m_discovery_function;
3571 class CommandObjectTypeFormat : public CommandObjectMultiword
3574 CommandObjectTypeFormat(CommandInterpreter &interpreter)
3575 : CommandObjectMultiword(interpreter, "type format", "Commands for customizing value display formats.",
3576 "type format [<sub-command-options>] ")
3578 LoadSubCommand ("add", CommandObjectSP (new CommandObjectTypeFormatAdd (interpreter)));
3579 LoadSubCommand ("clear", CommandObjectSP (new CommandObjectTypeFormatClear (interpreter)));
3580 LoadSubCommand ("delete", CommandObjectSP (new CommandObjectTypeFormatDelete (interpreter)));
3581 LoadSubCommand ("list", CommandObjectSP (new CommandObjectTypeFormatList (interpreter)));
3582 LoadSubCommand ("info", CommandObjectSP (new CommandObjectFormatterInfo<TypeFormatImpl>(interpreter,
3584 [](ValueObject& valobj) -> TypeFormatImpl::SharedPointer {
3585 return valobj.GetValueFormat();
3589 ~CommandObjectTypeFormat() override = default;
3592 #ifndef LLDB_DISABLE_PYTHON
3594 class CommandObjectTypeSynth : public CommandObjectMultiword
3597 CommandObjectTypeSynth(CommandInterpreter &interpreter)
3598 : CommandObjectMultiword(interpreter, "type synthetic",
3599 "Commands for operating on synthetic type representations.",
3600 "type synthetic [<sub-command-options>] ")
3602 LoadSubCommand ("add", CommandObjectSP (new CommandObjectTypeSynthAdd (interpreter)));
3603 LoadSubCommand ("clear", CommandObjectSP (new CommandObjectTypeSynthClear (interpreter)));
3604 LoadSubCommand ("delete", CommandObjectSP (new CommandObjectTypeSynthDelete (interpreter)));
3605 LoadSubCommand ("list", CommandObjectSP (new CommandObjectTypeSynthList (interpreter)));
3606 LoadSubCommand ("info", CommandObjectSP (new CommandObjectFormatterInfo<SyntheticChildren>(interpreter,
3608 [](ValueObject& valobj) -> SyntheticChildren::SharedPointer {
3609 return valobj.GetSyntheticChildren();
3613 ~CommandObjectTypeSynth() override = default;
3616 #endif // LLDB_DISABLE_PYTHON
3618 class CommandObjectTypeFilter : public CommandObjectMultiword
3621 CommandObjectTypeFilter(CommandInterpreter &interpreter)
3622 : CommandObjectMultiword(interpreter, "type filter", "Commands for operating on type filters.",
3623 "type synthetic [<sub-command-options>] ")
3625 LoadSubCommand ("add", CommandObjectSP (new CommandObjectTypeFilterAdd (interpreter)));
3626 LoadSubCommand ("clear", CommandObjectSP (new CommandObjectTypeFilterClear (interpreter)));
3627 LoadSubCommand ("delete", CommandObjectSP (new CommandObjectTypeFilterDelete (interpreter)));
3628 LoadSubCommand ("list", CommandObjectSP (new CommandObjectTypeFilterList (interpreter)));
3631 ~CommandObjectTypeFilter() override = default;
3634 class CommandObjectTypeCategory : public CommandObjectMultiword
3637 CommandObjectTypeCategory(CommandInterpreter &interpreter)
3638 : CommandObjectMultiword(interpreter, "type category", "Commands for operating on type categories.",
3639 "type category [<sub-command-options>] ")
3641 LoadSubCommand ("define", CommandObjectSP (new CommandObjectTypeCategoryDefine (interpreter)));
3642 LoadSubCommand ("enable", CommandObjectSP (new CommandObjectTypeCategoryEnable (interpreter)));
3643 LoadSubCommand ("disable", CommandObjectSP (new CommandObjectTypeCategoryDisable (interpreter)));
3644 LoadSubCommand ("delete", CommandObjectSP (new CommandObjectTypeCategoryDelete (interpreter)));
3645 LoadSubCommand ("list", CommandObjectSP (new CommandObjectTypeCategoryList (interpreter)));
3648 ~CommandObjectTypeCategory() override = default;
3651 class CommandObjectTypeSummary : public CommandObjectMultiword
3654 CommandObjectTypeSummary(CommandInterpreter &interpreter)
3655 : CommandObjectMultiword(interpreter, "type summary", "Commands for editing variable summary display options.",
3656 "type summary [<sub-command-options>] ")
3658 LoadSubCommand ("add", CommandObjectSP (new CommandObjectTypeSummaryAdd (interpreter)));
3659 LoadSubCommand ("clear", CommandObjectSP (new CommandObjectTypeSummaryClear (interpreter)));
3660 LoadSubCommand ("delete", CommandObjectSP (new CommandObjectTypeSummaryDelete (interpreter)));
3661 LoadSubCommand ("list", CommandObjectSP (new CommandObjectTypeSummaryList (interpreter)));
3662 LoadSubCommand ("info", CommandObjectSP (new CommandObjectFormatterInfo<TypeSummaryImpl>(interpreter,
3664 [](ValueObject& valobj) -> TypeSummaryImpl::SharedPointer {
3665 return valobj.GetSummaryFormat();
3669 ~CommandObjectTypeSummary() override = default;
3672 //-------------------------------------------------------------------------
3673 // CommandObjectType
3674 //-------------------------------------------------------------------------
3676 CommandObjectType::CommandObjectType(CommandInterpreter &interpreter)
3677 : CommandObjectMultiword(interpreter, "type", "Commands for operating on the type system.",
3678 "type [<sub-command-options>]")
3680 LoadSubCommand ("category", CommandObjectSP (new CommandObjectTypeCategory (interpreter)));
3681 LoadSubCommand ("filter", CommandObjectSP (new CommandObjectTypeFilter (interpreter)));
3682 LoadSubCommand ("format", CommandObjectSP (new CommandObjectTypeFormat (interpreter)));
3683 LoadSubCommand ("summary", CommandObjectSP (new CommandObjectTypeSummary (interpreter)));
3684 #ifndef LLDB_DISABLE_PYTHON
3685 LoadSubCommand ("synthetic", CommandObjectSP (new CommandObjectTypeSynth (interpreter)));
3686 #endif // LLDB_DISABLE_PYTHON
3687 LoadSubCommand ("lookup", CommandObjectSP (new CommandObjectTypeLookup (interpreter)));
3690 CommandObjectType::~CommandObjectType() = default;