57#include "llvm/ADT/STLExtras.h"
58#include "llvm/ADT/StringRef.h"
59#include "llvm/Support/Compiler.h"
60#include "llvm/TargetParser/Triple.h"
104 Definition(
"flags", EntryType::FrameRegisterFlags),
105 Definition(
"no-debug", EntryType::FrameNoDebug),
108 Definition(
"is-artificial", EntryType::FrameIsArtificial),
114 Definition(
"name-without-args", EntryType::FunctionNameNoArgs),
115 Definition(
"name-with-args", EntryType::FunctionNameWithArgs),
116 Definition(
"mangled-name", EntryType::FunctionMangledName),
117 Definition(
"addr-offset", EntryType::FunctionAddrOffset),
118 Definition(
"concrete-only-addr-offset-no-padding",
119 EntryType::FunctionAddrOffsetConcrete),
120 Definition(
"line-offset", EntryType::FunctionLineOffset),
121 Definition(
"pc-offset", EntryType::FunctionPCOffset),
122 Definition(
"initial-function", EntryType::FunctionInitial),
123 Definition(
"changed", EntryType::FunctionChanged),
124 Definition(
"is-optimized", EntryType::FunctionIsOptimized)};
129 Definition(
"number", EntryType::LineEntryLineNumber),
130 Definition(
"column", EntryType::LineEntryColumn),
131 Definition(
"start-addr", EntryType::LineEntryStartAddress),
132 Definition(
"end-addr", EntryType::LineEntryEndAddress),
152 Definition(
"protocol_id", EntryType::ThreadProtocolID),
153 Definition(
"index", EntryType::ThreadIndexID),
158 Definition(
"stop-reason", EntryType::ThreadStopReason),
159 Definition(
"stop-reason-raw", EntryType::ThreadStopReasonRaw),
160 Definition(
"return-value", EntryType::ThreadReturnValue),
161 Definition(
"completed-expression", EntryType::ThreadCompletedExpression)};
166#define _TO_STR2(_val) #_val
167#define _TO_STR(_val) _TO_STR2(_val)
224 Definition(
"process", EntryType::ScriptProcess),
225 Definition(
"target", EntryType::ScriptTarget),
226 Definition(
"thread", EntryType::ScriptThread),
228 Definition(
"svar", EntryType::ScriptVariableSynthetic),
229 Definition(
"thread", EntryType::ScriptThread)};
234 Definition(
"addr-file-or-load", EntryType::AddressLoadOrFile),
236 Definition(
"current-pc-arrow", EntryType::CurrentPCArrow),
265 : string(s.
data(), s.size()), printf_format(), children(),
266 type(
Type::String) {}
269 : string(1, ch), printf_format(), children(), type(
Type::String) {}
273 children.push_back(
Entry(ch));
275 children.back().string.append(1, ch);
280 children.push_back(
Entry(s));
282 children.back().string.append(s.data(), s.size());
286 return AppendText(llvm::StringRef(cstr));
289#define ENUM_TO_CSTR(eee) \
290 case FormatEntity::Entry::Type::eee: \
364 s.
Printf(
"%*.*s%-20s: ", depth * 2, depth * 2,
"", TypeToCString(type));
368 s.
Printf(
"string = \"%s\"",
string.c_str());
369 if (!printf_format.empty())
370 s.
Printf(
"printf_format = \"%s\"", printf_format.c_str());
372 s.
Printf(
"number = %" PRIu64
" (0x%" PRIx64
"), ", number, number);
374 s.
Printf(
"deref = true, ");
376 for (
const auto &child : children) {
377 child.Dump(s, depth + 1);
384 const char *script_function_name) {
390 if (script_interpreter) {
392 std::string script_output;
395 script_output,
error) &&
397 s.
Printf(
"%s", script_output.c_str());
410 bool print_file_addr_or_load_addr) {
420 if (exe_ctx && target) {
425 if (print_file_addr_or_load_addr) {
432 s.
Printf(
"0x%*.*" PRIx64, addr_width, addr_width, vaddr);
442 bool concrete_only,
bool no_padding,
443 bool print_zero_offsets) {
450 if (sc->
block && !concrete_only) {
457 format_addr, inline_range))
465 const char *addr_offset_padding = no_padding ?
"" :
" ";
470 if (addr_file_addr > func_file_addr ||
471 (addr_file_addr == func_file_addr && print_zero_offsets)) {
472 s.
Printf(
"%s+%s%" PRIu64, addr_offset_padding, addr_offset_padding,
473 addr_file_addr - func_file_addr);
474 }
else if (addr_file_addr < func_file_addr) {
475 s.
Printf(
"%s-%s%" PRIu64, addr_offset_padding, addr_offset_padding,
476 func_file_addr - addr_file_addr);
484 if (addr_load_addr > func_load_addr ||
485 (addr_load_addr == func_load_addr && print_zero_offsets)) {
486 s.
Printf(
"%s+%s%" PRIu64, addr_offset_padding, addr_offset_padding,
487 addr_load_addr - func_load_addr);
488 }
else if (addr_load_addr < func_load_addr) {
489 s.
Printf(
"%s-%s%" PRIu64, addr_offset_padding, addr_offset_padding,
490 func_load_addr - addr_load_addr);
501 size_t &close_bracket_index,
502 const char *&var_name_final_if_array_range,
503 int64_t &index_lower, int64_t &index_higher) {
505 close_bracket_index = llvm::StringRef::npos;
506 const size_t open_bracket_index = subpath.find(
'[');
507 if (open_bracket_index == llvm::StringRef::npos) {
509 "[ScanBracketedRange] no bracketed range, skipping entirely");
513 close_bracket_index = subpath.find(
']', open_bracket_index + 1);
515 if (close_bracket_index == llvm::StringRef::npos) {
517 "[ScanBracketedRange] no bracketed range, skipping entirely");
520 var_name_final_if_array_range = subpath.data() + open_bracket_index;
522 if (close_bracket_index - open_bracket_index == 1) {
525 "[ScanBracketedRange] '[]' detected.. going from 0 to end of data");
528 const size_t separator_index = subpath.find(
'-', open_bracket_index + 1);
530 if (separator_index == llvm::StringRef::npos) {
531 const char *index_lower_cstr = subpath.data() + open_bracket_index + 1;
532 index_lower = ::strtoul(index_lower_cstr,
nullptr, 0);
533 index_higher = index_lower;
535 "[ScanBracketedRange] [%" PRId64
536 "] detected, high index is same",
539 const char *index_lower_cstr = subpath.data() + open_bracket_index + 1;
540 const char *index_higher_cstr = subpath.data() + separator_index + 1;
541 index_lower = ::strtoul(index_lower_cstr,
nullptr, 0);
542 index_higher = ::strtoul(index_higher_cstr,
nullptr, 0);
544 "[ScanBracketedRange] [%" PRId64
"-%" PRId64
"] detected",
545 index_lower, index_higher);
547 if (index_lower > index_higher && index_higher > 0) {
548 LLDB_LOGF(log,
"[ScanBracketedRange] swapping indices");
549 const int64_t temp = index_lower;
550 index_lower = index_higher;
560 case FileKind::FileError:
563 case FileKind::Basename:
570 case FileKind::Dirname:
577 case FileKind::Fullpath:
588 uint32_t reg_num,
Format format) {
593 const uint32_t lldb_reg_num =
612 bool deref_pointer) {
614 std::string name_to_deref = llvm::formatv(
"[{0}]", index);
615 LLDB_LOG(log,
"[ExpandIndexedExpression] name to deref: {0}", name_to_deref);
623 name_to_deref, &reason_to_stop, &final_value_type, options, &what_next);
626 "[ExpandIndexedExpression] ERROR: why stopping = %d,"
627 " final_value_type %d",
628 reason_to_stop, final_value_type);
631 "[ExpandIndexedExpression] ALL RIGHT: why stopping = %d,"
632 " final_value_type %d",
633 reason_to_stop, final_value_type);
664 if (valobj ==
nullptr)
674 bool do_deref_pointer = entry.
deref;
675 bool is_script =
false;
676 switch (entry.
type) {
682 custom_format = entry.
fmt;
690 custom_format = entry.
fmt;
694 if (valobj ==
nullptr)
712 SyntheticChildrenTraversal::Both);
714 const char *var_name_final_if_array_range =
nullptr;
715 size_t close_bracket_index = llvm::StringRef::npos;
716 int64_t index_lower = -1;
717 int64_t index_higher = -1;
718 bool is_array_range =
false;
719 bool was_plain_var =
false;
720 bool was_var_format =
false;
721 bool was_var_indexed =
false;
731 llvm::StringRef subpath(entry.
string);
733 if (entry.
string.empty()) {
736 was_plain_var =
true;
738 was_var_format =
true;
742 if (entry.
string[0] ==
'[')
743 was_var_indexed =
true;
745 var_name_final_if_array_range, index_lower,
750 const std::string &expr_path = entry.
string;
752 LLDB_LOGF(log,
"[Debugger::FormatPrompt] symbol to expand: %s",
758 &final_value_type, options, &what_next)
763 "[Debugger::FormatPrompt] ERROR: why stopping = %d,"
764 " final_value_type %d",
765 reason_to_stop, final_value_type);
769 "[Debugger::FormatPrompt] ALL RIGHT: why stopping = %d,"
770 " final_value_type %d",
771 reason_to_stop, final_value_type);
788 if (do_deref_pointer && !is_array_range) {
795 LLDB_LOGF(log,
"[Debugger::FormatPrompt] ERROR: %s\n",
796 error.AsCString(
"unknown"));
799 do_deref_pointer =
false;
803 LLDB_LOGF(log,
"[Debugger::FormatPrompt] could not calculate target for "
804 "prompt expression");
811 if (target->
IsBitfield() && was_var_indexed) {
816 auto type_sp = std::make_shared<TypeNameSpecifierImpl>(
818 if (val_obj_display ==
825 const uint32_t type_info_flags =
827 bool is_array = (type_info_flags & eTypeIsArray) != 0;
828 bool is_pointer = (type_info_flags & eTypeIsPointer) != 0;
831 if ((is_array || is_pointer) && (!is_array_range) &&
840 "[Debugger::FormatPrompt] I am into array || pointer && !range");
846 str_temp, val_obj_display, custom_format);
847 LLDB_LOGF(log,
"[Debugger::FormatPrompt] special cases did%s match",
848 success ?
"" :
"n't");
858 }
else if (is_pointer)
861 s, val_obj_display, custom_format,
870 if (is_aggregate && was_plain_var) {
881 s <<
"<invalid use of aggregate type>";
885 if (!is_array_range) {
887 "[Debugger::FormatPrompt] dumping ordinary printable output");
892 "[Debugger::FormatPrompt] checking if I can handle as array");
893 if (!is_array && !is_pointer)
895 LLDB_LOGF(log,
"[Debugger::FormatPrompt] handle as array");
897 llvm::StringRef special_directions;
898 if (close_bracket_index != llvm::StringRef::npos &&
899 subpath.size() > close_bracket_index) {
900 ConstString additional_data(subpath.drop_front(close_bracket_index + 1));
901 special_directions_stream.
Printf(
"${%svar%s", do_deref_pointer ?
"*" :
"",
905 const char format_char =
907 if (format_char !=
'\0')
908 special_directions_stream.
Printf(
"%%%c", format_char);
910 const char *format_cstr =
912 special_directions_stream.
Printf(
"%%%s", format_cstr);
914 }
else if (entry.
number != 0) {
918 special_directions_stream.
Printf(
"%%%c", style_char);
920 special_directions_stream.
PutChar(
'}');
922 llvm::StringRef(special_directions_stream.
GetString());
928 if (index_higher < 0)
931 uint32_t max_num_children =
932 target->
GetTargetSP()->GetMaximumNumberOfChildrenToDisplay();
935 for (int64_t index = index_lower; index <= index_higher; ++index) {
940 "[Debugger::FormatPrompt] ERROR in getting child item at "
946 "[Debugger::FormatPrompt] special_directions for child item: %s",
947 special_directions.data() ? special_directions.data() :
"");
950 if (special_directions.empty()) {
955 special_directions, s, sc, exe_ctx,
nullptr, item,
false,
false);
958 if (--max_num_children == 0) {
963 if (index < index_higher)
994 llvm::StringRef path(entry.
string);
997 thread_info_dictionary->GetObjectForDotSeparatedPath(path);
1001 const char *token_format =
"0x%4.4" PRIx64;
1004 s.
Printf(token_format, value->GetUnsignedIntegerValue());
1007 s.
Printf(
"%f", value->GetAsFloat()->GetValue());
1010 s.
Format(
"{0}", value->GetAsString()->GetValue());
1013 if (value->GetAsArray()->GetSize() > 0) {
1014 s.
Printf(
"%zu", value->GetAsArray()->GetSize());
1019 value->GetAsDictionary()->GetKeys()->GetAsArray()->GetSize());
1027static inline bool IsToken(
const char *var_name_begin,
const char *var) {
1028 return (::strncmp(var_name_begin, var, strlen(var)) == 0);
1038static std::pair<char const *, char const *>
1040 const char *open_paren = strchr(full_name,
'(');
1041 const char *close_paren =
nullptr;
1042 const char *
generic = strchr(full_name,
'<');
1046 if (generic && open_paren && generic < open_paren) {
1047 int generic_depth = 1;
1049 for (; *
generic && generic_depth > 0;
generic++) {
1050 if (*generic ==
'<')
1052 if (*generic ==
'>')
1056 open_paren = strchr(generic,
'(');
1058 open_paren =
nullptr;
1062 if (
IsToken(open_paren,
"(anonymous namespace)")) {
1063 open_paren = strchr(open_paren + strlen(
"(anonymous namespace)"),
'(');
1065 close_paren = strchr(open_paren,
')');
1067 close_paren = strchr(open_paren,
')');
1070 return {open_paren, close_paren};
1077 char const *full_name,
1082 out_stream.
Write(full_name, open_paren - full_name + 1);
1104 inline_info->GetName().Dump(&out_stream);
1113 bool function_changed,
1114 bool initial_function) {
1115 if (!format_str.empty()) {
1118 if (
error.Success()) {
1120 function_changed, initial_function);
1130 bool function_changed,
bool initial_function) {
1131 if (format && format[0]) {
1133 llvm::StringRef format_str(format);
1135 if (
error.Success()) {
1137 function_changed, initial_function);
1147 bool initial_function) {
1148 switch (entry.
type) {
1158 Debugger &debugger = target->GetDebugger();
1168 for (
const auto &child : entry.
children) {
1169 if (!
Format(child, s, sc, exe_ctx, addr, valobj, function_changed,
1170 initial_function)) {
1182 bool success =
false;
1183 for (
const auto &child : entry.
children) {
1184 success =
Format(child, scope_stream, sc, exe_ctx, addr, valobj,
1185 function_changed, initial_function);
1200 return DumpValue(s, sc, exe_ctx, entry, valobj);
1206 addr !=
nullptr && addr->
IsValid() &&
1214 const char *format =
"%" PRIu64;
1249 const char *format =
"0x%4.4" PRIx64;
1258 llvm::Triple::OSType ostype = arch.
IsValid()
1260 : llvm::Triple::UnknownOS;
1261 if (ostype == llvm::Triple::FreeBSD ||
1262 ostype == llvm::Triple::Linux ||
1263 ostype == llvm::Triple::NetBSD ||
1264 ostype == llvm::Triple::OpenBSD) {
1265 format =
"%" PRIu64;
1281 const char *format =
"0x%4.4" PRIx64;
1294 const char *format =
"%" PRIu32;
1307 const char *cstr = thread->
GetName();
1308 if (cstr && cstr[0]) {
1321 if (cstr && cstr[0]) {
1332 std::string stop_description = thread->GetStopDescription();
1333 if (!stop_description.empty()) {
1344 std::string stop_description = thread->GetStopDescriptionRaw();
1345 if (!stop_description.empty()) {
1358 if (stop_info_sp && stop_info_sp->IsValid()) {
1361 if (return_valobj_sp) {
1362 return_valobj_sp->Dump(s);
1375 if (stop_info_sp && stop_info_sp->IsValid()) {
1378 if (expression_var_sp && expression_var_sp->GetValueObject()) {
1379 expression_var_sp->GetValueObject()->Dump(s);
1456 const char *lang_name =
1470 const char *format =
"%" PRIu32;
1548 return frame->IsArtificial();
1574 return function_changed;
1577 return initial_function;
1583 Language *language_plugin =
nullptr;
1584 bool language_plugin_handled =
false;
1592 if (language_plugin)
1596 if (language_plugin_handled) {
1600 const char *name =
nullptr;
1619 Language *language_plugin =
nullptr;
1620 bool language_plugin_handled =
false;
1627 if (language_plugin)
1632 if (language_plugin_handled) {
1654 Language *language_plugin =
nullptr;
1655 bool language_plugin_handled =
false;
1662 if (language_plugin)
1666 if (language_plugin_handled) {
1678 bool get_function_vars =
true;
1683 get_function_vars =
false;
1690 if (get_function_vars) {
1702 if (variable_list_sp)
1727 const char *name =
nullptr;
1778 return function_changed;
1781 bool is_optimized =
false;
1783 is_optimized =
true;
1785 return is_optimized;
1789 return initial_function;
1803 const char *format =
"%" PRIu32;
1813 const char *format =
"%" PRIu32;
1838 addr_t pc_loadaddr = reg_ctx->GetPC();
1860 for (
size_t i = 0; i < n; ++i) {
1874 const size_t sep_pos = format_str.find_first_of(
".[:");
1875 const char sep_char =
1876 (sep_pos == llvm::StringRef::npos) ?
'\0' : format_str[sep_pos];
1877 llvm::StringRef key = format_str.substr(0, sep_pos);
1880 for (
size_t i = 0; i < n; ++i) {
1882 if (key.equals(entry_def->
name) || entry_def->
name[0] ==
'*') {
1883 llvm::StringRef value;
1886 format_str.substr(sep_pos + (entry_def->
keep_separator ? 0 : 1));
1887 switch (entry_def->
type) {
1889 entry.
string = format_str.str();
1906 if (value.empty()) {
1910 error_strm.
Printf(
"'%s' can't be specified on its own, you must "
1911 "access one of its children: ",
1914 error.SetErrorStringWithFormat(
"%s", error_strm.
GetData());
1915 }
else if (sep_char ==
':') {
1921 error.SetErrorStringWithFormat(
"%s",
"invalid entry definitions");
1927 }
else if (sep_char ==
':') {
1931 entry.
string = value.str();
1933 error.SetErrorStringWithFormat(
1934 "'%s' followed by '%s' but it has no children", key.str().c_str(),
1935 value.str().c_str());
1944 "invalid top level item '%s'. Valid top level items are: ",
1947 error_strm.
Printf(
"invalid member '%s' in '%s'. Valid members are: ",
1948 key.str().c_str(), parent->
name);
1950 error.SetErrorStringWithFormat(
"%s", error_strm.
GetData());
1956 llvm::StringRef &remainder) {
1959 std::pair<llvm::StringRef, llvm::StringRef> p = format_str.split(
'.');
1961 for (
size_t i = 0; i < n; ++i) {
1963 if (p.first.equals(entry_def->
name) || entry_def->
name[0] ==
'*') {
1964 if (p.second.empty()) {
1965 if (format_str.back() ==
'.')
1966 remainder = format_str.drop_front(format_str.size() - 1);
1968 remainder = llvm::StringRef();
1972 return FindEntry(p.second, entry_def, remainder);
1974 remainder = p.second;
1980 remainder = format_str;
1987 while (!format.empty() &&
error.Success()) {
1988 const size_t non_special_chars = format.find_first_of(
"${}\\");
1990 if (non_special_chars == llvm::StringRef::npos) {
1996 if (non_special_chars > 0) {
1999 parent_entry.
AppendText(format.substr(0, non_special_chars));
2000 format = format.drop_front(non_special_chars);
2003 switch (format[0]) {
2008 format = format.drop_front();
2018 error.SetErrorString(
"unmatched '}' character");
2026 format = format.drop_front();
2027 if (format.empty()) {
2028 error.SetErrorString(
2029 "'\\' character was not followed by another character");
2033 const char desens_char = format[0];
2034 format = format.drop_front();
2035 switch (desens_char) {
2068 char oct_str[5] = {0, 0, 0, 0, 0};
2071 for (i = 0; (format[i] >=
'0' && format[i] <=
'7') && i < 4; ++i)
2072 oct_str[i] = format[i];
2077 format = format.drop_front(i);
2078 unsigned long octal_value = ::strtoul(oct_str,
nullptr, 8);
2079 if (octal_value <= UINT8_MAX) {
2082 error.SetErrorString(
"octal number is larger than a single byte");
2090 if (isxdigit(format[0])) {
2093 char hex_str[3] = {0, 0, 0};
2094 hex_str[0] = format[0];
2096 format = format.drop_front();
2098 if (isxdigit(format[0])) {
2099 hex_str[1] = format[0];
2100 format = format.drop_front();
2103 unsigned long hex_value = strtoul(hex_str,
nullptr, 16);
2104 if (hex_value <= UINT8_MAX) {
2107 error.SetErrorString(
"hex number is larger than a single byte");
2124 if (format.size() == 1) {
2128 format = format.drop_front();
2130 if (format[0] ==
'{') {
2131 format = format.drop_front();
2133 llvm::StringRef variable, variable_format;
2138 bool verify_is_thread_id =
false;
2140 if (!variable_format.empty()) {
2152 bool clear_printf =
false;
2159 clear_printf =
true;
2165 clear_printf =
true;
2170 clear_printf =
true;
2175 clear_printf =
true;
2180 clear_printf =
true;
2185 clear_printf =
true;
2190 clear_printf =
true;
2195 clear_printf =
true;
2203 clear_printf =
true;
2205 verify_is_thread_id =
true;
2207 error.SetErrorStringWithFormat(
"invalid format: '%s'",
2221 if (variable[0] ==
'*') {
2223 variable = variable.drop_front();
2230 if (verify_is_thread_id) {
2233 error.SetErrorString(
"the 'tid' format can only be used on "
2234 "${thread.id} and ${thread.protocol_id}");
2238 switch (entry.
type) {
2242 if (entry.
string.empty())
2254 error.SetErrorStringWithFormat(
2255 "${%s} can't be dereferenced, only ${var} and ${svar} can.",
2256 variable.str().c_str());
2270 llvm::StringRef &variable_name,
2271 llvm::StringRef &variable_format) {
2273 variable_name = llvm::StringRef();
2274 variable_format = llvm::StringRef();
2276 const size_t paren_pos = format_str.find(
'}');
2277 if (paren_pos != llvm::StringRef::npos) {
2278 const size_t percent_pos = format_str.find(
'%');
2279 if (percent_pos < paren_pos) {
2280 if (percent_pos > 0) {
2281 if (percent_pos > 1)
2282 variable_name = format_str.substr(0, percent_pos);
2284 format_str.substr(percent_pos + 1, paren_pos - (percent_pos + 1));
2287 variable_name = format_str.substr(0, paren_pos);
2290 format_str = format_str.substr(paren_pos + 1);
2292 error.SetErrorStringWithFormat(
2293 "missing terminating '}' character for '${%s'",
2294 format_str.str().c_str());
2300 llvm::StringRef variable_name,
2301 llvm::StringRef variable_format) {
2302 if (variable_name.empty() || variable_name.equals(
".fullpath")) {
2305 }
else if (variable_name.equals(
".basename")) {
2308 }
else if (variable_name.equals(
".dirname")) {
2316 const char *suffix) {
2317 std::string match(prefix.str());
2318 match.append(suffix);
2323 const llvm::StringRef &match_prefix,
2327 for (
size_t i = 0; i < n; ++i) {
2328 std::string match = prefix.str();
2329 if (match_prefix.empty())
2331 else if (strncmp(def->
children[i].
name, match_prefix.data(),
2332 match_prefix.size()) == 0)
2342 const size_t dollar_pos = str.rfind(
'$');
2343 if (dollar_pos == llvm::StringRef::npos)
2347 if (dollar_pos == str.size() - 1) {
2348 std::string match = str.str();
2354 if (str[dollar_pos + 1] !=
'{')
2357 const size_t close_pos = str.find(
'}', dollar_pos + 2);
2358 if (close_pos != llvm::StringRef::npos)
2361 const size_t format_pos = str.find(
'%', dollar_pos + 2);
2362 if (format_pos != llvm::StringRef::npos)
2365 llvm::StringRef partial_variable(str.substr(dollar_pos + 2));
2366 if (partial_variable.empty()) {
2375 llvm::StringRef remainder;
2382 if (remainder.empty()) {
2391 }
else if (remainder.equals(
".")) {
2394 AddMatches(entry_def, str, llvm::StringRef(), new_matches);
2400 AddMatches(entry_def, str, remainder, new_matches);
2408 const size_t num_args = args.
GetSize();
2409 for (
size_t arg_idx = 0; arg_idx < num_args; ++arg_idx) {
2415 llvm::StringRef var_representation;
2416 const char *var_name = var_value_sp->GetName().GetCString();
2417 if (var_value_sp->GetCompilerType().IsValid()) {
2419 var_value_sp = var_value_sp->GetQualifiedRepresentationIfAvailable(
2421 ->TargetProperties::GetPreferDynamicValue(),
2423 ->TargetProperties::GetEnableSyntheticValue());
2424 if (var_value_sp->GetCompilerType().IsAggregateType() &&
2427 .SetHideItemNames(
false)
2428 .SetShowMembersOneLiner(
true),
2431 var_representation = buffer;
2433 var_value_sp->DumpPrintableRepresentation(
2436 eValueObjectRepresentationStyleSummary,
2445 if (var_value_sp->GetError().Success()) {
2446 if (!var_representation.empty())
2447 out_stream.
Printf(
"%s=%s", var_name, var_representation.str().c_str());
2449 out_stream.
Printf(
"%s=%s at %s", var_name,
2450 var_value_sp->GetTypeName().GetCString(),
2451 var_value_sp->GetLocationAsCString());
2453 out_stream.
Printf(
"%s=<unavailable>", var_name);
2460 llvm::StringRef modifiable_format(format_str);
#define ANSI_BG_COLOR_PURPLE
#define ANSI_CTRL_UNDERLINE
#define ANSI_BG_COLOR_RED
#define ANSI_FG_COLOR_BLACK
#define ANSI_BG_COLOR_YELLOW
#define ANSI_BG_COLOR_BLACK
#define ANSI_FG_COLOR_YELLOW
#define ANSI_FG_COLOR_PURPLE
#define ANSI_BG_COLOR_CYAN
#define ANSI_BG_COLOR_GREEN
#define ANSI_CTRL_SLOW_BLINK
#define ANSI_FG_COLOR_RED
#define ANSI_BG_COLOR_BLUE
#define ANSI_FG_COLOR_CYAN
#define ANSI_CTRL_FAST_BLINK
#define ANSI_CTRL_CROSSED_OUT
#define ANSI_CTRL_IMAGE_NEGATIVE
#define ANSI_BG_COLOR_WHITE
#define ANSI_CTRL_CONCEAL
#define ANSI_FG_COLOR_GREEN
#define ANSI_FG_COLOR_BLUE
#define ANSI_FG_COLOR_WHITE
static llvm::raw_ostream & error(Stream &strm)
#define LLDB_LOG(log,...)
The LLDB_LOG* macros defined below are the way to emit log messages.
#define LLDB_LOGF(log,...)
A section + offset based address range class.
Address & GetBaseAddress()
Get accessor for the base address of the range.
lldb::addr_t GetByteSize() const
Get accessor for the byte size of this range.
A section + offset based address class.
lldb::addr_t GetLoadAddress(Target *target) const
Get the load address.
lldb::SectionSP GetSection() const
Get const accessor for the section.
@ DumpStyleModuleWithFileAddress
Display as the file address with the module name prepended (if any).
@ DumpStyleLoadAddress
Display as the load address (if resolved).
bool Slide(int64_t offset)
bool Dump(Stream *s, ExecutionContextScope *exe_scope, DumpStyle style, DumpStyle fallback_style=DumpStyleInvalid, uint32_t addr_byte_size=UINT32_MAX, bool all_ranges=false, std::optional< Stream::HighlightSettings > settings=std::nullopt) const
Dump a description of this object to a Stream.
lldb::addr_t GetFileAddress() const
Get the file address.
bool IsValid() const
Check if the object state is valid.
An architecture specification class.
uint32_t GetAddressByteSize() const
Returns the size in bytes of an address of the current architecture.
bool IsValid() const
Tests if this ArchSpec is valid.
llvm::Triple & GetTriple()
Architecture triple accessor.
const char * GetArchitectureName() const
Returns a static string representing the current architecture.
A class that describes a single lexical block.
lldb::VariableListSP GetBlockVariableList(bool can_create)
Get the variable list for this block only.
Block * GetContainingInlinedBlock()
Get the inlined block that contains this block.
const InlineFunctionInfo * GetInlinedFunctionInfo() const
Get const accessor for any inlined function information.
bool GetRangeContainingAddress(const Address &addr, AddressRange &range)
A class that describes a compilation unit.
const FileSpec & GetPrimaryFile() const
Return the primary source spec associated with this compile unit.
lldb::LanguageType GetLanguage()
bool IsAggregateType() const
uint32_t GetTypeInfo(CompilerType *pointee_or_element_compiler_type=nullptr) const
"lldb/Utility/ArgCompletionRequest.h"
void AddCompletion(llvm::StringRef completion, llvm::StringRef description="", CompletionMode mode=CompletionMode::Normal)
Adds a possible completion string.
void AddCompletions(const StringList &completions)
Adds multiple possible completion strings.
llvm::StringRef GetCursorArgumentPrefix() const
A uniqued constant string class.
const char * AsCString(const char *value_if_empty=nullptr) const
Get the string value as a C string.
llvm::StringRef GetStringRef() const
Get the string value as a llvm::StringRef.
const char * GetCString() const
Get the string value as a C string.
static bool ShouldPrintAsOneLiner(ValueObject &valobj)
static lldb::TypeSummaryImplSP GetSummaryForType(lldb::TypeNameSpecifierImplSP type_sp)
A class to manage flag bits.
ScriptInterpreter * GetScriptInterpreter(bool can_create=true, std::optional< lldb::ScriptLanguage > language={})
"lldb/Target/ExecutionContextScope.h" Inherit from this if your object can reconstruct its execution ...
virtual lldb::TargetSP CalculateTarget()=0
"lldb/Target/ExecutionContext.h" A class that contains an execution context.
ExecutionContextScope * GetBestExecutionContextScope() const
StackFrame * GetFramePtr() const
Returns a pointer to the frame object.
Target * GetTargetPtr() const
Returns a pointer to the target object.
Process * GetProcessPtr() const
Returns a pointer to the process object.
Thread * GetThreadPtr() const
Returns a pointer to the thread object.
const ConstString & GetFilename() const
Filename string const get accessor.
const ConstString & GetDirectory() const
Directory string const get accessor.
void Dump(llvm::raw_ostream &s) const
Dump this object to a Stream.
An abstract base class for files.
bool GetIsOptimized()
Get whether compiler optimizations were enabled for this function.
const AddressRange & GetAddressRange()
ConstString GetName() const
const Mangled & GetMangled() const
lldb::LanguageType GetLanguage() const
ConstString GetNameNoArguments() const
Block & GetBlock(bool can_create)
Get accessor for the block list.
A class that describes information for an inlined function.
ConstString GetName() const
static Language * FindPlugin(lldb::LanguageType language)
static const char * GetNameForLanguageType(lldb::LanguageType language)
virtual bool GetFunctionDisplayName(const SymbolContext *sc, const ExecutionContext *exe_ctx, FunctionNameRepresentation representation, Stream &s)
ConstString GetName(NamePreference preference=ePreferDemangled) const
Best name get accessor.
A class that describes an executable image and its associated object and symbol files.
const FileSpec & GetFileSpec() const
Get const accessor for the module file specification.
A plug-in interface definition class for debugging a process.
lldb::pid_t GetID() const
Returns the pid of the process or LLDB_INVALID_PROCESS_ID if there is no known pid.
Target & GetTarget()
Get the target object pointer for this module.
virtual uint32_t ConvertRegisterKindToRegisterNumber(lldb::RegisterKind kind, uint32_t num)
Convert from a given register numbering scheme to the lldb register numbering scheme.
virtual const RegisterInfo * GetRegisterInfoAtIndex(size_t reg)=0
const RegisterInfo * GetRegisterInfoByName(llvm::StringRef reg_name, uint32_t start_idx=0)
virtual bool ReadRegister(const RegisterInfo *reg_info, RegisterValue ®_value)=0
virtual bool RunScriptFormatKeyword(const char *impl_function, Process *process, std::string &output, Status &error)
This base class provides an interface to stack frames.
lldb::RegisterContextSP GetRegisterContext()
Get the RegisterContext for this frame, if possible.
uint32_t GetFrameIndex() const
Query this frame to find what frame it is in this Thread's StackFrameList.
bool HasDebugInformation()
Determine whether this StackFrame has debug information available or not.
const lldb::RegisterContextSP & GetRegisterContextSP() const
const Address & GetFrameCodeAddress()
Get an Address for the current pc value in this StackFrame.
static lldb::ExpressionVariableSP GetExpressionVariable(lldb::StopInfoSP &stop_info_sp)
static lldb::ValueObjectSP GetReturnValueObject(lldb::StopInfoSP &stop_info_sp)
const char * GetData() const
llvm::StringRef GetString() const
A stream class that can stream formatted output to a file.
void Format(const char *format, Args &&... args)
size_t Write(const void *src, size_t src_len)
Output character bytes to the stream.
llvm::raw_ostream & AsRawOstream()
Returns a raw_ostream that forwards the data to this Stream object.
size_t Printf(const char *format,...) __attribute__((format(printf
Output printf formatted output to the stream.
size_t PutCString(llvm::StringRef cstr)
Output a C string to the stream.
size_t EOL()
Output and End of Line character to the stream.
void AppendString(const std::string &s)
std::shared_ptr< Object > ObjectSP
Defines a symbol context baton that can be handed other debug core functions.
Function * function
The Function for a given query.
Block * block
The Block for a given query.
lldb::ModuleSP module_sp
The Module for a given query.
CompileUnit * comp_unit
The CompileUnit for a given query.
Symbol * symbol
The Symbol for a given query.
LineEntry line_entry
The LineEntry for a given query.
bool ValueIsAddress() const
lldb::LanguageType GetLanguage() const
Address & GetAddressRef()
ConstString GetName() const
ConstString GetNameNoArguments() const
Module * GetExecutableModulePointer()
static Target * GetTargetFromContexts(const ExecutionContext *exe_ctx_ptr, const SymbolContext *sc_ptr)
SectionLoadList & GetSectionLoadList()
const ArchSpec & GetArchitecture() const
virtual lldb::user_id_t GetProtocolID() const
virtual const char * GetQueueName()
Retrieve the Queue name for the queue currently using this Thread.
uint32_t GetIndexID() const
StructuredData::ObjectSP GetExtendedInfo()
Retrieve a dictionary of information about this thread.
virtual const char * GetName()
lldb::ProcessSP GetProcess() const
lldb::StopInfoSP GetStopInfo()
static lldb::ValueObjectSP Create(ExecutionContextScope *exe_scope, const lldb::VariableSP &var_sp)
virtual uint32_t GetBitfieldBitSize()
bool DumpPrintableRepresentation(Stream &s, ValueObjectRepresentationStyle val_obj_display=eValueObjectRepresentationStyleSummary, lldb::Format custom_format=lldb::eFormatInvalid, PrintableRepresentationSpecialCases special=PrintableRepresentationSpecialCases::eAllow, bool do_dump_error=true)
CompilerType GetCompilerType()
lldb::ValueObjectSP GetSyntheticValue()
ExpressionPathScanEndReason
@ eExpressionPathScanEndReasonEndOfString
Out of data to parse.
@ eExpressionPathAftermathNothing
Just return it.
@ eExpressionPathAftermathDereference
Dereference the target.
lldb::ValueObjectSP GetValueForExpressionPath(llvm::StringRef expression, ExpressionPathScanEndReason *reason_to_stop=nullptr, ExpressionPathEndResultType *final_value_type=nullptr, const GetValueForExpressionPathOptions &options=GetValueForExpressionPathOptions::DefaultOptions(), ExpressionPathAftermath *final_task_on_target=nullptr)
virtual ConstString GetTypeName()
lldb::DynamicValueType GetDynamicValueType()
lldb::ValueObjectSP GetQualifiedRepresentationIfAvailable(lldb::DynamicValueType dynValue, bool synthValue)
lldb::TargetSP GetTargetSP() const
ExpressionPathEndResultType
@ eExpressionPathEndResultTypePlain
Anything but...
@ eExpressionPathEndResultTypeBoundedRange
A range [low-high].
@ eExpressionPathEndResultTypeUnboundedRange
A range [].
virtual lldb::ValueObjectSP Dereference(Status &error)
bool HasSpecialPrintableRepresentation(ValueObjectRepresentationStyle val_obj_display, lldb::Format custom_format)
virtual const char * GetLocationAsCString()
ValueObjectRepresentationStyle
@ eValueObjectRepresentationStyleLocation
@ eValueObjectRepresentationStyleSummary
@ eValueObjectRepresentationStyleName
@ eValueObjectRepresentationStyleType
@ eValueObjectRepresentationStyleChildrenCount
@ eValueObjectRepresentationStyleExpressionPath
@ eValueObjectRepresentationStyleValue
@ eValueObjectRepresentationStyleLanguageSpecific
virtual bool IsSynthetic()
uint32_t GetNumChildrenIgnoringErrors(uint32_t max=UINT32_MAX)
Like GetNumChildren but returns 0 on error.
lldb::VariableSP GetVariableAtIndex(size_t idx) const
size_t AppendVariablesWithScope(lldb::ValueType type, VariableList &var_list, bool if_unique=true)
#define LLDB_REGNUM_GENERIC_SP
#define LLDB_REGNUM_GENERIC_FLAGS
#define LLDB_INVALID_ADDRESS
#define LLDB_INVALID_REGNUM
#define LLDB_REGNUM_GENERIC_FP
A class that represents a running process on the host machine.
Log * GetLog(Cat mask)
Retrieve the Log object for the channel associated with the given log enum.
void DumpRegisterValue(const RegisterValue ®_val, Stream &s, const RegisterInfo ®_info, bool prefix_with_name, bool prefix_with_alt_name, lldb::Format format, uint32_t reg_name_right_align_at=0, ExecutionContextScope *exe_scope=nullptr, bool print_flags=false, lldb::TargetSP target_sp=nullptr)
std::shared_ptr< lldb_private::ValueObject > ValueObjectSP
std::shared_ptr< lldb_private::ExpressionVariable > ExpressionVariableSP
Format
Display format definitions.
std::shared_ptr< lldb_private::VariableList > VariableListSP
std::shared_ptr< lldb_private::Variable > VariableSP
std::shared_ptr< lldb_private::StopInfo > StopInfoSP
@ eStructuredDataTypeFloat
@ eStructuredDataTypeDictionary
@ eStructuredDataTypeInteger
@ eStructuredDataTypeArray
@ eStructuredDataTypeString
std::shared_ptr< lldb_private::RegisterContext > RegisterContextSP
@ eValueTypeVariableArgument
function argument variables
RegisterKind
Register numbering types.
@ eRegisterKindGeneric
insn ptr reg, stack ptr reg, etc not specific to any particular target
const char * name
The name/string placeholder that corresponds to this definition.
const Definition * children
An array of "num_children" Definition entries.
const bool keep_separator
Whether the separator is kept during parsing or not.
const char * string
Insert this exact string into the output.
const uint64_t data
Data that is returned as the value of the format string.
const uint32_t num_children
The number of children of this node in the tree of format strings.
const Entry::Type type
Entry::Type corresponding to this definition.
void Dump(Stream &s, int depth=0) const
std::vector< Entry > children
void AppendText(const llvm::StringRef &s)
static constexpr Definition DefinitionWithChildren(const char *name, const FormatEntity::Entry::Type t, const Definition(&children)[N], bool keep_separator=false)
std::string printf_format
void AppendEntry(const Entry &&entry)
static const char * TypeToCString(Type t)
@ FunctionAddrOffsetConcrete
@ FunctionInitialFunction
@ ThreadCompletedExpression
@ ScriptVariableSynthetic
Entry(Type t=Type::Invalid, const char *s=nullptr, const char *f=nullptr)
uint16_t column
The column number of the source line, or zero if there is no column information.
bool IsValid() const
Check if a line entry object is valid.
AddressRange range
The section offset address range for this line entry.
uint32_t line
The source line number, or LLDB_INVALID_LINE_NUMBER if there is no line number information.
const FileSpec & GetFile() const
Every register is described in detail including its name, alternate name (optional),...
llvm::ArrayRef< uint8_t > data(const uint8_t *context_base) const
lldb::user_id_t GetID() const
Get accessor for the user ID.
GetValueForExpressionPathOptions & SetSyntheticChildrenTraversal(SyntheticChildrenTraversal traverse)
GetValueForExpressionPathOptions & DoAllowFragileIVar()
GetValueForExpressionPathOptions & DontCheckDotVsArrowSyntax()
GetValueForExpressionPathOptions & DoAllowBitfieldSyntax()