aboutsummaryrefslogtreecommitdiff
path: root/lldb/source/Symbol/ClangASTContext.cpp
diff options
context:
space:
mode:
authorKate Stone <katherine.stone@apple.com>2016-09-06 20:57:50 +0000
committerKate Stone <katherine.stone@apple.com>2016-09-06 20:57:50 +0000
commitb9c1b51e45b845debb76d8658edabca70ca56079 (patch)
treedfcb5a13ef2b014202340f47036da383eaee74aa /lldb/source/Symbol/ClangASTContext.cpp
parentd5aa73376966339caad04013510626ec2e42c760 (diff)
downloadllvm-b9c1b51e45b845debb76d8658edabca70ca56079.zip
llvm-b9c1b51e45b845debb76d8658edabca70ca56079.tar.gz
llvm-b9c1b51e45b845debb76d8658edabca70ca56079.tar.bz2
*** This commit represents a complete reformatting of the LLDB source code
*** to conform to clang-format’s LLVM style. This kind of mass change has *** two obvious implications: Firstly, merging this particular commit into a downstream fork may be a huge effort. Alternatively, it may be worth merging all changes up to this commit, performing the same reformatting operation locally, and then discarding the merge for this particular commit. The commands used to accomplish this reformatting were as follows (with current working directory as the root of the repository): find . \( -iname "*.c" -or -iname "*.cpp" -or -iname "*.h" -or -iname "*.mm" \) -exec clang-format -i {} + find . -iname "*.py" -exec autopep8 --in-place --aggressive --aggressive {} + ; The version of clang-format used was 3.9.0, and autopep8 was 1.2.4. Secondly, “blame” style tools will generally point to this commit instead of a meaningful prior commit. There are alternatives available that will attempt to look through this change and find the appropriate prior commit. YMMV. llvm-svn: 280751
Diffstat (limited to 'lldb/source/Symbol/ClangASTContext.cpp')
-rw-r--r--lldb/source/Symbol/ClangASTContext.cpp18266
1 files changed, 9062 insertions, 9204 deletions
diff --git a/lldb/source/Symbol/ClangASTContext.cpp b/lldb/source/Symbol/ClangASTContext.cpp
index 21cfeff..e7fda6d 100644
--- a/lldb/source/Symbol/ClangASTContext.cpp
+++ b/lldb/source/Symbol/ClangASTContext.cpp
@@ -17,7 +17,7 @@
// Other libraries and framework includes
-// Clang headers like to use NDEBUG inside of them to enable/disable debug
+// Clang headers like to use NDEBUG inside of them to enable/disable debug
// related features using "#ifndef NDEBUG" preprocessor blocks to do one thing
// or another. This is bad because it means that if clang was built in release
// mode, it assumes that you are building in release mode which is not always
@@ -103,2350 +103,2072 @@ using namespace lldb_private;
using namespace llvm;
using namespace clang;
-namespace
-{
- static inline bool ClangASTContextSupportsLanguage (lldb::LanguageType language)
- {
- return language == eLanguageTypeUnknown || // Clang is the default type system
- Language::LanguageIsC(language) ||
- Language::LanguageIsCPlusPlus(language) ||
- Language::LanguageIsObjC(language) ||
- Language::LanguageIsPascal(language) ||
- // Use Clang for Rust until there is a proper language plugin for it
- language == eLanguageTypeRust ||
- language == eLanguageTypeExtRenderScript;
- }
+namespace {
+static inline bool
+ClangASTContextSupportsLanguage(lldb::LanguageType language) {
+ return language == eLanguageTypeUnknown || // Clang is the default type system
+ Language::LanguageIsC(language) ||
+ Language::LanguageIsCPlusPlus(language) ||
+ Language::LanguageIsObjC(language) ||
+ Language::LanguageIsPascal(language) ||
+ // Use Clang for Rust until there is a proper language plugin for it
+ language == eLanguageTypeRust ||
+ language == eLanguageTypeExtRenderScript;
+}
}
-typedef lldb_private::ThreadSafeDenseMap<clang::ASTContext *, ClangASTContext*> ClangASTMap;
+typedef lldb_private::ThreadSafeDenseMap<clang::ASTContext *, ClangASTContext *>
+ ClangASTMap;
-static ClangASTMap &
-GetASTMap()
-{
- static ClangASTMap *g_map_ptr = nullptr;
- static std::once_flag g_once_flag;
- std::call_once(g_once_flag, []() {
- g_map_ptr = new ClangASTMap(); // leaked on purpose to avoid spins
- });
- return *g_map_ptr;
+static ClangASTMap &GetASTMap() {
+ static ClangASTMap *g_map_ptr = nullptr;
+ static std::once_flag g_once_flag;
+ std::call_once(g_once_flag, []() {
+ g_map_ptr = new ClangASTMap(); // leaked on purpose to avoid spins
+ });
+ return *g_map_ptr;
}
-static bool
-IsOperator(const char *name, clang::OverloadedOperatorKind &op_kind)
-{
- if (name == nullptr || name[0] == '\0')
- return false;
+static bool IsOperator(const char *name,
+ clang::OverloadedOperatorKind &op_kind) {
+ if (name == nullptr || name[0] == '\0')
+ return false;
#define OPERATOR_PREFIX "operator"
#define OPERATOR_PREFIX_LENGTH (sizeof(OPERATOR_PREFIX) - 1)
- const char *post_op_name = nullptr;
+ const char *post_op_name = nullptr;
- bool no_space = true;
+ bool no_space = true;
- if (::strncmp(name, OPERATOR_PREFIX, OPERATOR_PREFIX_LENGTH))
- return false;
+ if (::strncmp(name, OPERATOR_PREFIX, OPERATOR_PREFIX_LENGTH))
+ return false;
- post_op_name = name + OPERATOR_PREFIX_LENGTH;
+ post_op_name = name + OPERATOR_PREFIX_LENGTH;
- if (post_op_name[0] == ' ')
- {
- post_op_name++;
- no_space = false;
- }
+ if (post_op_name[0] == ' ') {
+ post_op_name++;
+ no_space = false;
+ }
#undef OPERATOR_PREFIX
#undef OPERATOR_PREFIX_LENGTH
- // This is an operator, set the overloaded operator kind to invalid
- // in case this is a conversion operator...
- op_kind = clang::NUM_OVERLOADED_OPERATORS;
-
- switch (post_op_name[0])
- {
- default:
- if (no_space)
- return false;
- break;
- case 'n':
- if (no_space)
- return false;
- if (strcmp(post_op_name, "new") == 0)
- op_kind = clang::OO_New;
- else if (strcmp(post_op_name, "new[]") == 0)
- op_kind = clang::OO_Array_New;
- break;
-
- case 'd':
- if (no_space)
- return false;
- if (strcmp(post_op_name, "delete") == 0)
- op_kind = clang::OO_Delete;
- else if (strcmp(post_op_name, "delete[]") == 0)
- op_kind = clang::OO_Array_Delete;
- break;
-
- case '+':
- if (post_op_name[1] == '\0')
- op_kind = clang::OO_Plus;
- else if (post_op_name[2] == '\0')
- {
- if (post_op_name[1] == '=')
- op_kind = clang::OO_PlusEqual;
- else if (post_op_name[1] == '+')
- op_kind = clang::OO_PlusPlus;
- }
- break;
-
- case '-':
- if (post_op_name[1] == '\0')
- op_kind = clang::OO_Minus;
- else if (post_op_name[2] == '\0')
- {
- switch (post_op_name[1])
- {
- case '=':
- op_kind = clang::OO_MinusEqual;
- break;
- case '-':
- op_kind = clang::OO_MinusMinus;
- break;
- case '>':
- op_kind = clang::OO_Arrow;
- break;
- }
- }
- else if (post_op_name[3] == '\0')
- {
- if (post_op_name[2] == '*')
- op_kind = clang::OO_ArrowStar;
- break;
- }
- break;
+ // This is an operator, set the overloaded operator kind to invalid
+ // in case this is a conversion operator...
+ op_kind = clang::NUM_OVERLOADED_OPERATORS;
+
+ switch (post_op_name[0]) {
+ default:
+ if (no_space)
+ return false;
+ break;
+ case 'n':
+ if (no_space)
+ return false;
+ if (strcmp(post_op_name, "new") == 0)
+ op_kind = clang::OO_New;
+ else if (strcmp(post_op_name, "new[]") == 0)
+ op_kind = clang::OO_Array_New;
+ break;
+
+ case 'd':
+ if (no_space)
+ return false;
+ if (strcmp(post_op_name, "delete") == 0)
+ op_kind = clang::OO_Delete;
+ else if (strcmp(post_op_name, "delete[]") == 0)
+ op_kind = clang::OO_Array_Delete;
+ break;
+
+ case '+':
+ if (post_op_name[1] == '\0')
+ op_kind = clang::OO_Plus;
+ else if (post_op_name[2] == '\0') {
+ if (post_op_name[1] == '=')
+ op_kind = clang::OO_PlusEqual;
+ else if (post_op_name[1] == '+')
+ op_kind = clang::OO_PlusPlus;
+ }
+ break;
+
+ case '-':
+ if (post_op_name[1] == '\0')
+ op_kind = clang::OO_Minus;
+ else if (post_op_name[2] == '\0') {
+ switch (post_op_name[1]) {
+ case '=':
+ op_kind = clang::OO_MinusEqual;
+ break;
+ case '-':
+ op_kind = clang::OO_MinusMinus;
+ break;
+ case '>':
+ op_kind = clang::OO_Arrow;
+ break;
+ }
+ } else if (post_op_name[3] == '\0') {
+ if (post_op_name[2] == '*')
+ op_kind = clang::OO_ArrowStar;
+ break;
+ }
+ break;
+
+ case '*':
+ if (post_op_name[1] == '\0')
+ op_kind = clang::OO_Star;
+ else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
+ op_kind = clang::OO_StarEqual;
+ break;
+
+ case '/':
+ if (post_op_name[1] == '\0')
+ op_kind = clang::OO_Slash;
+ else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
+ op_kind = clang::OO_SlashEqual;
+ break;
+
+ case '%':
+ if (post_op_name[1] == '\0')
+ op_kind = clang::OO_Percent;
+ else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
+ op_kind = clang::OO_PercentEqual;
+ break;
+
+ case '^':
+ if (post_op_name[1] == '\0')
+ op_kind = clang::OO_Caret;
+ else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
+ op_kind = clang::OO_CaretEqual;
+ break;
+
+ case '&':
+ if (post_op_name[1] == '\0')
+ op_kind = clang::OO_Amp;
+ else if (post_op_name[2] == '\0') {
+ switch (post_op_name[1]) {
+ case '=':
+ op_kind = clang::OO_AmpEqual;
+ break;
+ case '&':
+ op_kind = clang::OO_AmpAmp;
+ break;
+ }
+ }
+ break;
- case '*':
- if (post_op_name[1] == '\0')
- op_kind = clang::OO_Star;
- else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
- op_kind = clang::OO_StarEqual;
- break;
+ case '|':
+ if (post_op_name[1] == '\0')
+ op_kind = clang::OO_Pipe;
+ else if (post_op_name[2] == '\0') {
+ switch (post_op_name[1]) {
+ case '=':
+ op_kind = clang::OO_PipeEqual;
+ break;
+ case '|':
+ op_kind = clang::OO_PipePipe;
+ break;
+ }
+ }
+ break;
+
+ case '~':
+ if (post_op_name[1] == '\0')
+ op_kind = clang::OO_Tilde;
+ break;
+
+ case '!':
+ if (post_op_name[1] == '\0')
+ op_kind = clang::OO_Exclaim;
+ else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
+ op_kind = clang::OO_ExclaimEqual;
+ break;
+
+ case '=':
+ if (post_op_name[1] == '\0')
+ op_kind = clang::OO_Equal;
+ else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
+ op_kind = clang::OO_EqualEqual;
+ break;
+
+ case '<':
+ if (post_op_name[1] == '\0')
+ op_kind = clang::OO_Less;
+ else if (post_op_name[2] == '\0') {
+ switch (post_op_name[1]) {
+ case '<':
+ op_kind = clang::OO_LessLess;
+ break;
+ case '=':
+ op_kind = clang::OO_LessEqual;
+ break;
+ }
+ } else if (post_op_name[3] == '\0') {
+ if (post_op_name[2] == '=')
+ op_kind = clang::OO_LessLessEqual;
+ }
+ break;
+
+ case '>':
+ if (post_op_name[1] == '\0')
+ op_kind = clang::OO_Greater;
+ else if (post_op_name[2] == '\0') {
+ switch (post_op_name[1]) {
+ case '>':
+ op_kind = clang::OO_GreaterGreater;
+ break;
+ case '=':
+ op_kind = clang::OO_GreaterEqual;
+ break;
+ }
+ } else if (post_op_name[1] == '>' && post_op_name[2] == '=' &&
+ post_op_name[3] == '\0') {
+ op_kind = clang::OO_GreaterGreaterEqual;
+ }
+ break;
- case '/':
- if (post_op_name[1] == '\0')
- op_kind = clang::OO_Slash;
- else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
- op_kind = clang::OO_SlashEqual;
- break;
+ case ',':
+ if (post_op_name[1] == '\0')
+ op_kind = clang::OO_Comma;
+ break;
- case '%':
- if (post_op_name[1] == '\0')
- op_kind = clang::OO_Percent;
- else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
- op_kind = clang::OO_PercentEqual;
- break;
+ case '(':
+ if (post_op_name[1] == ')' && post_op_name[2] == '\0')
+ op_kind = clang::OO_Call;
+ break;
- case '^':
- if (post_op_name[1] == '\0')
- op_kind = clang::OO_Caret;
- else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
- op_kind = clang::OO_CaretEqual;
- break;
+ case '[':
+ if (post_op_name[1] == ']' && post_op_name[2] == '\0')
+ op_kind = clang::OO_Subscript;
+ break;
+ }
- case '&':
- if (post_op_name[1] == '\0')
- op_kind = clang::OO_Amp;
- else if (post_op_name[2] == '\0')
- {
- switch (post_op_name[1])
- {
- case '=':
- op_kind = clang::OO_AmpEqual;
- break;
- case '&':
- op_kind = clang::OO_AmpAmp;
- break;
- }
- }
- break;
+ return true;
+}
- case '|':
- if (post_op_name[1] == '\0')
- op_kind = clang::OO_Pipe;
- else if (post_op_name[2] == '\0')
- {
- switch (post_op_name[1])
- {
- case '=':
- op_kind = clang::OO_PipeEqual;
- break;
- case '|':
- op_kind = clang::OO_PipePipe;
- break;
- }
- }
- break;
+clang::AccessSpecifier
+ClangASTContext::ConvertAccessTypeToAccessSpecifier(AccessType access) {
+ switch (access) {
+ default:
+ break;
+ case eAccessNone:
+ return AS_none;
+ case eAccessPublic:
+ return AS_public;
+ case eAccessPrivate:
+ return AS_private;
+ case eAccessProtected:
+ return AS_protected;
+ }
+ return AS_none;
+}
+
+static void ParseLangArgs(LangOptions &Opts, InputKind IK, const char *triple) {
+ // FIXME: Cleanup per-file based stuff.
+
+ // Set some properties which depend solely on the input kind; it would be nice
+ // to move these to the language standard, and have the driver resolve the
+ // input kind + language standard.
+ if (IK == IK_Asm) {
+ Opts.AsmPreprocessor = 1;
+ } else if (IK == IK_ObjC || IK == IK_ObjCXX || IK == IK_PreprocessedObjC ||
+ IK == IK_PreprocessedObjCXX) {
+ Opts.ObjC1 = Opts.ObjC2 = 1;
+ }
+
+ LangStandard::Kind LangStd = LangStandard::lang_unspecified;
+
+ if (LangStd == LangStandard::lang_unspecified) {
+ // Based on the base language, pick one.
+ switch (IK) {
+ case IK_None:
+ case IK_AST:
+ case IK_LLVM_IR:
+ case IK_RenderScript:
+ assert(!"Invalid input kind!");
+ case IK_OpenCL:
+ LangStd = LangStandard::lang_opencl;
+ break;
+ case IK_CUDA:
+ case IK_PreprocessedCuda:
+ LangStd = LangStandard::lang_cuda;
+ break;
+ case IK_Asm:
+ case IK_C:
+ case IK_PreprocessedC:
+ case IK_ObjC:
+ case IK_PreprocessedObjC:
+ LangStd = LangStandard::lang_gnu99;
+ break;
+ case IK_CXX:
+ case IK_PreprocessedCXX:
+ case IK_ObjCXX:
+ case IK_PreprocessedObjCXX:
+ LangStd = LangStandard::lang_gnucxx98;
+ break;
+ }
+ }
+
+ const LangStandard &Std = LangStandard::getLangStandardForKind(LangStd);
+ Opts.LineComment = Std.hasLineComments();
+ Opts.C99 = Std.isC99();
+ Opts.CPlusPlus = Std.isCPlusPlus();
+ Opts.CPlusPlus11 = Std.isCPlusPlus11();
+ Opts.Digraphs = Std.hasDigraphs();
+ Opts.GNUMode = Std.isGNUMode();
+ Opts.GNUInline = !Std.isC99();
+ Opts.HexFloats = Std.hasHexFloats();
+ Opts.ImplicitInt = Std.hasImplicitInt();
+
+ Opts.WChar = true;
+
+ // OpenCL has some additional defaults.
+ if (LangStd == LangStandard::lang_opencl) {
+ Opts.OpenCL = 1;
+ Opts.AltiVec = 1;
+ Opts.CXXOperatorNames = 1;
+ Opts.LaxVectorConversions = 1;
+ }
+
+ // OpenCL and C++ both have bool, true, false keywords.
+ Opts.Bool = Opts.OpenCL || Opts.CPlusPlus;
+
+ // if (Opts.CPlusPlus)
+ // Opts.CXXOperatorNames = !Args.hasArg(OPT_fno_operator_names);
+ //
+ // if (Args.hasArg(OPT_fobjc_gc_only))
+ // Opts.setGCMode(LangOptions::GCOnly);
+ // else if (Args.hasArg(OPT_fobjc_gc))
+ // Opts.setGCMode(LangOptions::HybridGC);
+ //
+ // if (Args.hasArg(OPT_print_ivar_layout))
+ // Opts.ObjCGCBitmapPrint = 1;
+ //
+ // if (Args.hasArg(OPT_faltivec))
+ // Opts.AltiVec = 1;
+ //
+ // if (Args.hasArg(OPT_pthread))
+ // Opts.POSIXThreads = 1;
+ //
+ // llvm::StringRef Vis = getLastArgValue(Args, OPT_fvisibility,
+ // "default");
+ // if (Vis == "default")
+ Opts.setValueVisibilityMode(DefaultVisibility);
+ // else if (Vis == "hidden")
+ // Opts.setVisibilityMode(LangOptions::Hidden);
+ // else if (Vis == "protected")
+ // Opts.setVisibilityMode(LangOptions::Protected);
+ // else
+ // Diags.Report(diag::err_drv_invalid_value)
+ // << Args.getLastArg(OPT_fvisibility)->getAsString(Args) << Vis;
+
+ // Opts.OverflowChecking = Args.hasArg(OPT_ftrapv);
+
+ // Mimicing gcc's behavior, trigraphs are only enabled if -trigraphs
+ // is specified, or -std is set to a conforming mode.
+ Opts.Trigraphs = !Opts.GNUMode;
+ // if (Args.hasArg(OPT_trigraphs))
+ // Opts.Trigraphs = 1;
+ //
+ // Opts.DollarIdents = Args.hasFlag(OPT_fdollars_in_identifiers,
+ // OPT_fno_dollars_in_identifiers,
+ // !Opts.AsmPreprocessor);
+ // Opts.PascalStrings = Args.hasArg(OPT_fpascal_strings);
+ // Opts.Microsoft = Args.hasArg(OPT_fms_extensions);
+ // Opts.WritableStrings = Args.hasArg(OPT_fwritable_strings);
+ // if (Args.hasArg(OPT_fno_lax_vector_conversions))
+ // Opts.LaxVectorConversions = 0;
+ // Opts.Exceptions = Args.hasArg(OPT_fexceptions);
+ // Opts.RTTI = !Args.hasArg(OPT_fno_rtti);
+ // Opts.Blocks = Args.hasArg(OPT_fblocks);
+ Opts.CharIsSigned = ArchSpec(triple).CharIsSignedByDefault();
+ // Opts.ShortWChar = Args.hasArg(OPT_fshort_wchar);
+ // Opts.Freestanding = Args.hasArg(OPT_ffreestanding);
+ // Opts.NoBuiltin = Args.hasArg(OPT_fno_builtin) || Opts.Freestanding;
+ // Opts.AssumeSaneOperatorNew =
+ // !Args.hasArg(OPT_fno_assume_sane_operator_new);
+ // Opts.HeinousExtensions = Args.hasArg(OPT_fheinous_gnu_extensions);
+ // Opts.AccessControl = Args.hasArg(OPT_faccess_control);
+ // Opts.ElideConstructors = !Args.hasArg(OPT_fno_elide_constructors);
+ // Opts.MathErrno = !Args.hasArg(OPT_fno_math_errno);
+ // Opts.InstantiationDepth = getLastArgIntValue(Args, OPT_ftemplate_depth,
+ // 99,
+ // Diags);
+ // Opts.NeXTRuntime = !Args.hasArg(OPT_fgnu_runtime);
+ // Opts.ObjCConstantStringClass = getLastArgValue(Args,
+ // OPT_fconstant_string_class);
+ // Opts.ObjCNonFragileABI = Args.hasArg(OPT_fobjc_nonfragile_abi);
+ // Opts.CatchUndefined = Args.hasArg(OPT_fcatch_undefined_behavior);
+ // Opts.EmitAllDecls = Args.hasArg(OPT_femit_all_decls);
+ // Opts.PICLevel = getLastArgIntValue(Args, OPT_pic_level, 0, Diags);
+ // Opts.Static = Args.hasArg(OPT_static_define);
+ Opts.OptimizeSize = 0;
+
+ // FIXME: Eliminate this dependency.
+ // unsigned Opt =
+ // Args.hasArg(OPT_Os) ? 2 : getLastArgIntValue(Args, OPT_O, 0, Diags);
+ // Opts.Optimize = Opt != 0;
+ unsigned Opt = 0;
+
+ // This is the __NO_INLINE__ define, which just depends on things like the
+ // optimization level and -fno-inline, not actually whether the backend has
+ // inlining enabled.
+ //
+ // FIXME: This is affected by other options (-fno-inline).
+ Opts.NoInlineDefine = !Opt;
+
+ // unsigned SSP = getLastArgIntValue(Args, OPT_stack_protector, 0, Diags);
+ // switch (SSP) {
+ // default:
+ // Diags.Report(diag::err_drv_invalid_value)
+ // << Args.getLastArg(OPT_stack_protector)->getAsString(Args) <<
+ // SSP;
+ // break;
+ // case 0: Opts.setStackProtectorMode(LangOptions::SSPOff); break;
+ // case 1: Opts.setStackProtectorMode(LangOptions::SSPOn); break;
+ // case 2: Opts.setStackProtectorMode(LangOptions::SSPReq); break;
+ // }
+}
+
+ClangASTContext::ClangASTContext(const char *target_triple)
+ : TypeSystem(TypeSystem::eKindClang), m_target_triple(), m_ast_ap(),
+ m_language_options_ap(), m_source_manager_ap(), m_diagnostics_engine_ap(),
+ m_target_options_rp(), m_target_info_ap(), m_identifier_table_ap(),
+ m_selector_table_ap(), m_builtins_ap(), m_callback_tag_decl(nullptr),
+ m_callback_objc_decl(nullptr), m_callback_baton(nullptr),
+ m_pointer_byte_size(0), m_ast_owned(false) {
+ if (target_triple && target_triple[0])
+ SetTargetTriple(target_triple);
+}
- case '~':
- if (post_op_name[1] == '\0')
- op_kind = clang::OO_Tilde;
- break;
+//----------------------------------------------------------------------
+// Destructor
+//----------------------------------------------------------------------
+ClangASTContext::~ClangASTContext() { Finalize(); }
+
+ConstString ClangASTContext::GetPluginNameStatic() {
+ return ConstString("clang");
+}
+
+ConstString ClangASTContext::GetPluginName() {
+ return ClangASTContext::GetPluginNameStatic();
+}
+
+uint32_t ClangASTContext::GetPluginVersion() { return 1; }
+
+lldb::TypeSystemSP ClangASTContext::CreateInstance(lldb::LanguageType language,
+ lldb_private::Module *module,
+ Target *target) {
+ if (ClangASTContextSupportsLanguage(language)) {
+ ArchSpec arch;
+ if (module)
+ arch = module->GetArchitecture();
+ else if (target)
+ arch = target->GetArchitecture();
+
+ if (arch.IsValid()) {
+ ArchSpec fixed_arch = arch;
+ // LLVM wants this to be set to iOS or MacOSX; if we're working on
+ // a bare-boards type image, change the triple for llvm's benefit.
+ if (fixed_arch.GetTriple().getVendor() == llvm::Triple::Apple &&
+ fixed_arch.GetTriple().getOS() == llvm::Triple::UnknownOS) {
+ if (fixed_arch.GetTriple().getArch() == llvm::Triple::arm ||
+ fixed_arch.GetTriple().getArch() == llvm::Triple::aarch64 ||
+ fixed_arch.GetTriple().getArch() == llvm::Triple::thumb) {
+ fixed_arch.GetTriple().setOS(llvm::Triple::IOS);
+ } else {
+ fixed_arch.GetTriple().setOS(llvm::Triple::MacOSX);
+ }
+ }
- case '!':
- if (post_op_name[1] == '\0')
- op_kind = clang::OO_Exclaim;
- else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
- op_kind = clang::OO_ExclaimEqual;
- break;
+ if (module) {
+ std::shared_ptr<ClangASTContext> ast_sp(new ClangASTContext);
+ if (ast_sp) {
+ ast_sp->SetArchitecture(fixed_arch);
+ }
+ return ast_sp;
+ } else if (target && target->IsValid()) {
+ std::shared_ptr<ClangASTContextForExpressions> ast_sp(
+ new ClangASTContextForExpressions(*target));
+ if (ast_sp) {
+ ast_sp->SetArchitecture(fixed_arch);
+ ast_sp->m_scratch_ast_source_ap.reset(
+ new ClangASTSource(target->shared_from_this()));
+ ast_sp->m_scratch_ast_source_ap->InstallASTContext(
+ ast_sp->getASTContext());
+ llvm::IntrusiveRefCntPtr<clang::ExternalASTSource> proxy_ast_source(
+ ast_sp->m_scratch_ast_source_ap->CreateProxy());
+ ast_sp->SetExternalSource(proxy_ast_source);
+ return ast_sp;
+ }
+ }
+ }
+ }
+ return lldb::TypeSystemSP();
+}
- case '=':
- if (post_op_name[1] == '\0')
- op_kind = clang::OO_Equal;
- else if (post_op_name[1] == '=' && post_op_name[2] == '\0')
- op_kind = clang::OO_EqualEqual;
- break;
+void ClangASTContext::EnumerateSupportedLanguages(
+ std::set<lldb::LanguageType> &languages_for_types,
+ std::set<lldb::LanguageType> &languages_for_expressions) {
+ static std::vector<lldb::LanguageType> s_supported_languages_for_types(
+ {lldb::eLanguageTypeC89, lldb::eLanguageTypeC, lldb::eLanguageTypeC11,
+ lldb::eLanguageTypeC_plus_plus, lldb::eLanguageTypeC99,
+ lldb::eLanguageTypeObjC, lldb::eLanguageTypeObjC_plus_plus,
+ lldb::eLanguageTypeC_plus_plus_03, lldb::eLanguageTypeC_plus_plus_11,
+ lldb::eLanguageTypeC11, lldb::eLanguageTypeC_plus_plus_14});
- case '<':
- if (post_op_name[1] == '\0')
- op_kind = clang::OO_Less;
- else if (post_op_name[2] == '\0')
- {
- switch (post_op_name[1])
- {
- case '<':
- op_kind = clang::OO_LessLess;
- break;
- case '=':
- op_kind = clang::OO_LessEqual;
- break;
- }
- }
- else if (post_op_name[3] == '\0')
- {
- if (post_op_name[2] == '=')
- op_kind = clang::OO_LessLessEqual;
- }
- break;
+ static std::vector<lldb::LanguageType> s_supported_languages_for_expressions(
+ {lldb::eLanguageTypeC_plus_plus, lldb::eLanguageTypeObjC_plus_plus,
+ lldb::eLanguageTypeC_plus_plus_03, lldb::eLanguageTypeC_plus_plus_11,
+ lldb::eLanguageTypeC_plus_plus_14});
- case '>':
- if (post_op_name[1] == '\0')
- op_kind = clang::OO_Greater;
- else if (post_op_name[2] == '\0')
- {
- switch (post_op_name[1])
- {
- case '>':
- op_kind = clang::OO_GreaterGreater;
- break;
- case '=':
- op_kind = clang::OO_GreaterEqual;
- break;
- }
- }
- else if (post_op_name[1] == '>' && post_op_name[2] == '=' && post_op_name[3] == '\0')
- {
- op_kind = clang::OO_GreaterGreaterEqual;
- }
- break;
+ languages_for_types.insert(s_supported_languages_for_types.begin(),
+ s_supported_languages_for_types.end());
+ languages_for_expressions.insert(
+ s_supported_languages_for_expressions.begin(),
+ s_supported_languages_for_expressions.end());
+}
- case ',':
- if (post_op_name[1] == '\0')
- op_kind = clang::OO_Comma;
- break;
+void ClangASTContext::Initialize() {
+ PluginManager::RegisterPlugin(GetPluginNameStatic(),
+ "clang base AST context plug-in",
+ CreateInstance, EnumerateSupportedLanguages);
+}
- case '(':
- if (post_op_name[1] == ')' && post_op_name[2] == '\0')
- op_kind = clang::OO_Call;
- break;
+void ClangASTContext::Terminate() {
+ PluginManager::UnregisterPlugin(CreateInstance);
+}
- case '[':
- if (post_op_name[1] == ']' && post_op_name[2] == '\0')
- op_kind = clang::OO_Subscript;
- break;
- }
+void ClangASTContext::Finalize() {
+ if (m_ast_ap.get()) {
+ GetASTMap().Erase(m_ast_ap.get());
+ if (!m_ast_owned)
+ m_ast_ap.release();
+ }
- return true;
+ m_builtins_ap.reset();
+ m_selector_table_ap.reset();
+ m_identifier_table_ap.reset();
+ m_target_info_ap.reset();
+ m_target_options_rp.reset();
+ m_diagnostics_engine_ap.reset();
+ m_source_manager_ap.reset();
+ m_language_options_ap.reset();
+ m_ast_ap.reset();
+ m_scratch_ast_source_ap.reset();
}
-clang::AccessSpecifier
-ClangASTContext::ConvertAccessTypeToAccessSpecifier (AccessType access)
-{
- switch (access)
- {
- default: break;
- case eAccessNone: return AS_none;
- case eAccessPublic: return AS_public;
- case eAccessPrivate: return AS_private;
- case eAccessProtected: return AS_protected;
- }
- return AS_none;
+void ClangASTContext::Clear() {
+ m_ast_ap.reset();
+ m_language_options_ap.reset();
+ m_source_manager_ap.reset();
+ m_diagnostics_engine_ap.reset();
+ m_target_options_rp.reset();
+ m_target_info_ap.reset();
+ m_identifier_table_ap.reset();
+ m_selector_table_ap.reset();
+ m_builtins_ap.reset();
+ m_pointer_byte_size = 0;
}
-static void
-ParseLangArgs (LangOptions &Opts, InputKind IK, const char* triple)
-{
- // FIXME: Cleanup per-file based stuff.
-
- // Set some properties which depend solely on the input kind; it would be nice
- // to move these to the language standard, and have the driver resolve the
- // input kind + language standard.
- if (IK == IK_Asm) {
- Opts.AsmPreprocessor = 1;
- } else if (IK == IK_ObjC ||
- IK == IK_ObjCXX ||
- IK == IK_PreprocessedObjC ||
- IK == IK_PreprocessedObjCXX) {
- Opts.ObjC1 = Opts.ObjC2 = 1;
- }
-
- LangStandard::Kind LangStd = LangStandard::lang_unspecified;
-
- if (LangStd == LangStandard::lang_unspecified) {
- // Based on the base language, pick one.
- switch (IK) {
- case IK_None:
- case IK_AST:
- case IK_LLVM_IR:
- case IK_RenderScript:
- assert (!"Invalid input kind!");
- case IK_OpenCL:
- LangStd = LangStandard::lang_opencl;
- break;
- case IK_CUDA:
- case IK_PreprocessedCuda:
- LangStd = LangStandard::lang_cuda;
- break;
- case IK_Asm:
- case IK_C:
- case IK_PreprocessedC:
- case IK_ObjC:
- case IK_PreprocessedObjC:
- LangStd = LangStandard::lang_gnu99;
- break;
- case IK_CXX:
- case IK_PreprocessedCXX:
- case IK_ObjCXX:
- case IK_PreprocessedObjCXX:
- LangStd = LangStandard::lang_gnucxx98;
- break;
- }
- }
-
- const LangStandard &Std = LangStandard::getLangStandardForKind(LangStd);
- Opts.LineComment = Std.hasLineComments();
- Opts.C99 = Std.isC99();
- Opts.CPlusPlus = Std.isCPlusPlus();
- Opts.CPlusPlus11 = Std.isCPlusPlus11();
- Opts.Digraphs = Std.hasDigraphs();
- Opts.GNUMode = Std.isGNUMode();
- Opts.GNUInline = !Std.isC99();
- Opts.HexFloats = Std.hasHexFloats();
- Opts.ImplicitInt = Std.hasImplicitInt();
-
- Opts.WChar = true;
-
- // OpenCL has some additional defaults.
- if (LangStd == LangStandard::lang_opencl) {
- Opts.OpenCL = 1;
- Opts.AltiVec = 1;
- Opts.CXXOperatorNames = 1;
- Opts.LaxVectorConversions = 1;
- }
-
- // OpenCL and C++ both have bool, true, false keywords.
- Opts.Bool = Opts.OpenCL || Opts.CPlusPlus;
-
-// if (Opts.CPlusPlus)
-// Opts.CXXOperatorNames = !Args.hasArg(OPT_fno_operator_names);
-//
-// if (Args.hasArg(OPT_fobjc_gc_only))
-// Opts.setGCMode(LangOptions::GCOnly);
-// else if (Args.hasArg(OPT_fobjc_gc))
-// Opts.setGCMode(LangOptions::HybridGC);
-//
-// if (Args.hasArg(OPT_print_ivar_layout))
-// Opts.ObjCGCBitmapPrint = 1;
-//
-// if (Args.hasArg(OPT_faltivec))
-// Opts.AltiVec = 1;
-//
-// if (Args.hasArg(OPT_pthread))
-// Opts.POSIXThreads = 1;
-//
-// llvm::StringRef Vis = getLastArgValue(Args, OPT_fvisibility,
-// "default");
-// if (Vis == "default")
- Opts.setValueVisibilityMode(DefaultVisibility);
-// else if (Vis == "hidden")
-// Opts.setVisibilityMode(LangOptions::Hidden);
-// else if (Vis == "protected")
-// Opts.setVisibilityMode(LangOptions::Protected);
-// else
-// Diags.Report(diag::err_drv_invalid_value)
-// << Args.getLastArg(OPT_fvisibility)->getAsString(Args) << Vis;
-
-// Opts.OverflowChecking = Args.hasArg(OPT_ftrapv);
-
- // Mimicing gcc's behavior, trigraphs are only enabled if -trigraphs
- // is specified, or -std is set to a conforming mode.
- Opts.Trigraphs = !Opts.GNUMode;
-// if (Args.hasArg(OPT_trigraphs))
-// Opts.Trigraphs = 1;
-//
-// Opts.DollarIdents = Args.hasFlag(OPT_fdollars_in_identifiers,
-// OPT_fno_dollars_in_identifiers,
-// !Opts.AsmPreprocessor);
-// Opts.PascalStrings = Args.hasArg(OPT_fpascal_strings);
-// Opts.Microsoft = Args.hasArg(OPT_fms_extensions);
-// Opts.WritableStrings = Args.hasArg(OPT_fwritable_strings);
-// if (Args.hasArg(OPT_fno_lax_vector_conversions))
-// Opts.LaxVectorConversions = 0;
-// Opts.Exceptions = Args.hasArg(OPT_fexceptions);
-// Opts.RTTI = !Args.hasArg(OPT_fno_rtti);
-// Opts.Blocks = Args.hasArg(OPT_fblocks);
- Opts.CharIsSigned = ArchSpec(triple).CharIsSignedByDefault();
-// Opts.ShortWChar = Args.hasArg(OPT_fshort_wchar);
-// Opts.Freestanding = Args.hasArg(OPT_ffreestanding);
-// Opts.NoBuiltin = Args.hasArg(OPT_fno_builtin) || Opts.Freestanding;
-// Opts.AssumeSaneOperatorNew = !Args.hasArg(OPT_fno_assume_sane_operator_new);
-// Opts.HeinousExtensions = Args.hasArg(OPT_fheinous_gnu_extensions);
-// Opts.AccessControl = Args.hasArg(OPT_faccess_control);
-// Opts.ElideConstructors = !Args.hasArg(OPT_fno_elide_constructors);
-// Opts.MathErrno = !Args.hasArg(OPT_fno_math_errno);
-// Opts.InstantiationDepth = getLastArgIntValue(Args, OPT_ftemplate_depth, 99,
-// Diags);
-// Opts.NeXTRuntime = !Args.hasArg(OPT_fgnu_runtime);
-// Opts.ObjCConstantStringClass = getLastArgValue(Args,
-// OPT_fconstant_string_class);
-// Opts.ObjCNonFragileABI = Args.hasArg(OPT_fobjc_nonfragile_abi);
-// Opts.CatchUndefined = Args.hasArg(OPT_fcatch_undefined_behavior);
-// Opts.EmitAllDecls = Args.hasArg(OPT_femit_all_decls);
-// Opts.PICLevel = getLastArgIntValue(Args, OPT_pic_level, 0, Diags);
-// Opts.Static = Args.hasArg(OPT_static_define);
- Opts.OptimizeSize = 0;
-
- // FIXME: Eliminate this dependency.
-// unsigned Opt =
-// Args.hasArg(OPT_Os) ? 2 : getLastArgIntValue(Args, OPT_O, 0, Diags);
-// Opts.Optimize = Opt != 0;
- unsigned Opt = 0;
-
- // This is the __NO_INLINE__ define, which just depends on things like the
- // optimization level and -fno-inline, not actually whether the backend has
- // inlining enabled.
- //
- // FIXME: This is affected by other options (-fno-inline).
- Opts.NoInlineDefine = !Opt;
-
-// unsigned SSP = getLastArgIntValue(Args, OPT_stack_protector, 0, Diags);
-// switch (SSP) {
-// default:
-// Diags.Report(diag::err_drv_invalid_value)
-// << Args.getLastArg(OPT_stack_protector)->getAsString(Args) << SSP;
-// break;
-// case 0: Opts.setStackProtectorMode(LangOptions::SSPOff); break;
-// case 1: Opts.setStackProtectorMode(LangOptions::SSPOn); break;
-// case 2: Opts.setStackProtectorMode(LangOptions::SSPReq); break;
-// }
-}
-
-
-ClangASTContext::ClangASTContext (const char *target_triple) :
- TypeSystem (TypeSystem::eKindClang),
- m_target_triple (),
- m_ast_ap (),
- m_language_options_ap (),
- m_source_manager_ap (),
- m_diagnostics_engine_ap (),
- m_target_options_rp (),
- m_target_info_ap (),
- m_identifier_table_ap (),
- m_selector_table_ap (),
- m_builtins_ap (),
- m_callback_tag_decl (nullptr),
- m_callback_objc_decl (nullptr),
- m_callback_baton (nullptr),
- m_pointer_byte_size (0),
- m_ast_owned (false)
-{
- if (target_triple && target_triple[0])
- SetTargetTriple (target_triple);
+const char *ClangASTContext::GetTargetTriple() {
+ return m_target_triple.c_str();
}
-//----------------------------------------------------------------------
-// Destructor
-//----------------------------------------------------------------------
-ClangASTContext::~ClangASTContext()
-{
- Finalize();
+void ClangASTContext::SetTargetTriple(const char *target_triple) {
+ Clear();
+ m_target_triple.assign(target_triple);
}
-ConstString
-ClangASTContext::GetPluginNameStatic()
-{
- return ConstString("clang");
+void ClangASTContext::SetArchitecture(const ArchSpec &arch) {
+ SetTargetTriple(arch.GetTriple().str().c_str());
}
-ConstString
-ClangASTContext::GetPluginName()
-{
- return ClangASTContext::GetPluginNameStatic();
+bool ClangASTContext::HasExternalSource() {
+ ASTContext *ast = getASTContext();
+ if (ast)
+ return ast->getExternalSource() != nullptr;
+ return false;
}
-uint32_t
-ClangASTContext::GetPluginVersion()
-{
- return 1;
+void ClangASTContext::SetExternalSource(
+ llvm::IntrusiveRefCntPtr<ExternalASTSource> &ast_source_ap) {
+ ASTContext *ast = getASTContext();
+ if (ast) {
+ ast->setExternalSource(ast_source_ap);
+ ast->getTranslationUnitDecl()->setHasExternalLexicalStorage(true);
+ // ast->getTranslationUnitDecl()->setHasExternalVisibleStorage(true);
+ }
}
-lldb::TypeSystemSP
-ClangASTContext::CreateInstance (lldb::LanguageType language,
- lldb_private::Module *module,
- Target *target)
-{
- if (ClangASTContextSupportsLanguage(language))
- {
- ArchSpec arch;
- if (module)
- arch = module->GetArchitecture();
- else if (target)
- arch = target->GetArchitecture();
-
- if (arch.IsValid())
- {
- ArchSpec fixed_arch = arch;
- // LLVM wants this to be set to iOS or MacOSX; if we're working on
- // a bare-boards type image, change the triple for llvm's benefit.
- if (fixed_arch.GetTriple().getVendor() == llvm::Triple::Apple &&
- fixed_arch.GetTriple().getOS() == llvm::Triple::UnknownOS)
- {
- if (fixed_arch.GetTriple().getArch() == llvm::Triple::arm ||
- fixed_arch.GetTriple().getArch() == llvm::Triple::aarch64 ||
- fixed_arch.GetTriple().getArch() == llvm::Triple::thumb)
- {
- fixed_arch.GetTriple().setOS(llvm::Triple::IOS);
- }
- else
- {
- fixed_arch.GetTriple().setOS(llvm::Triple::MacOSX);
- }
- }
+void ClangASTContext::RemoveExternalSource() {
+ ASTContext *ast = getASTContext();
- if (module)
- {
- std::shared_ptr<ClangASTContext> ast_sp(new ClangASTContext);
- if (ast_sp)
- {
- ast_sp->SetArchitecture (fixed_arch);
- }
- return ast_sp;
- }
- else if (target && target->IsValid())
- {
- std::shared_ptr<ClangASTContextForExpressions> ast_sp(new ClangASTContextForExpressions(*target));
- if (ast_sp)
- {
- ast_sp->SetArchitecture(fixed_arch);
- ast_sp->m_scratch_ast_source_ap.reset (new ClangASTSource(target->shared_from_this()));
- ast_sp->m_scratch_ast_source_ap->InstallASTContext(ast_sp->getASTContext());
- llvm::IntrusiveRefCntPtr<clang::ExternalASTSource> proxy_ast_source(ast_sp->m_scratch_ast_source_ap->CreateProxy());
- ast_sp->SetExternalSource(proxy_ast_source);
- return ast_sp;
- }
- }
- }
- }
- return lldb::TypeSystemSP();
-}
-
-void
-ClangASTContext::EnumerateSupportedLanguages(std::set<lldb::LanguageType> &languages_for_types, std::set<lldb::LanguageType> &languages_for_expressions)
-{
- static std::vector<lldb::LanguageType> s_supported_languages_for_types({
- lldb::eLanguageTypeC89,
- lldb::eLanguageTypeC,
- lldb::eLanguageTypeC11,
- lldb::eLanguageTypeC_plus_plus,
- lldb::eLanguageTypeC99,
- lldb::eLanguageTypeObjC,
- lldb::eLanguageTypeObjC_plus_plus,
- lldb::eLanguageTypeC_plus_plus_03,
- lldb::eLanguageTypeC_plus_plus_11,
- lldb::eLanguageTypeC11,
- lldb::eLanguageTypeC_plus_plus_14});
-
- static std::vector<lldb::LanguageType> s_supported_languages_for_expressions({
- lldb::eLanguageTypeC_plus_plus,
- lldb::eLanguageTypeObjC_plus_plus,
- lldb::eLanguageTypeC_plus_plus_03,
- lldb::eLanguageTypeC_plus_plus_11,
- lldb::eLanguageTypeC_plus_plus_14});
-
- languages_for_types.insert(s_supported_languages_for_types.begin(), s_supported_languages_for_types.end());
- languages_for_expressions.insert(s_supported_languages_for_expressions.begin(), s_supported_languages_for_expressions.end());
-}
-
-
-void
-ClangASTContext::Initialize()
-{
- PluginManager::RegisterPlugin (GetPluginNameStatic(),
- "clang base AST context plug-in",
- CreateInstance,
- EnumerateSupportedLanguages);
-}
-
-void
-ClangASTContext::Terminate()
-{
- PluginManager::UnregisterPlugin (CreateInstance);
-}
-
-void
-ClangASTContext::Finalize()
-{
- if (m_ast_ap.get())
- {
- GetASTMap().Erase(m_ast_ap.get());
- if (!m_ast_owned)
- m_ast_ap.release();
- }
-
- m_builtins_ap.reset();
- m_selector_table_ap.reset();
- m_identifier_table_ap.reset();
- m_target_info_ap.reset();
- m_target_options_rp.reset();
- m_diagnostics_engine_ap.reset();
- m_source_manager_ap.reset();
- m_language_options_ap.reset();
- m_ast_ap.reset();
- m_scratch_ast_source_ap.reset();
-}
-
-void
-ClangASTContext::Clear()
-{
- m_ast_ap.reset();
- m_language_options_ap.reset();
- m_source_manager_ap.reset();
- m_diagnostics_engine_ap.reset();
- m_target_options_rp.reset();
- m_target_info_ap.reset();
- m_identifier_table_ap.reset();
- m_selector_table_ap.reset();
- m_builtins_ap.reset();
- m_pointer_byte_size = 0;
-}
-
-const char *
-ClangASTContext::GetTargetTriple ()
-{
- return m_target_triple.c_str();
-}
-
-void
-ClangASTContext::SetTargetTriple (const char *target_triple)
-{
- Clear();
- m_target_triple.assign(target_triple);
-}
-
-void
-ClangASTContext::SetArchitecture (const ArchSpec &arch)
-{
- SetTargetTriple(arch.GetTriple().str().c_str());
-}
-
-bool
-ClangASTContext::HasExternalSource ()
-{
- ASTContext *ast = getASTContext();
- if (ast)
- return ast->getExternalSource () != nullptr;
- return false;
+ if (ast) {
+ llvm::IntrusiveRefCntPtr<ExternalASTSource> empty_ast_source_ap;
+ ast->setExternalSource(empty_ast_source_ap);
+ ast->getTranslationUnitDecl()->setHasExternalLexicalStorage(false);
+ // ast->getTranslationUnitDecl()->setHasExternalVisibleStorage(false);
+ }
}
-void
-ClangASTContext::SetExternalSource (llvm::IntrusiveRefCntPtr<ExternalASTSource> &ast_source_ap)
-{
- ASTContext *ast = getASTContext();
- if (ast)
- {
- ast->setExternalSource (ast_source_ap);
- ast->getTranslationUnitDecl()->setHasExternalLexicalStorage(true);
- //ast->getTranslationUnitDecl()->setHasExternalVisibleStorage(true);
- }
+void ClangASTContext::setASTContext(clang::ASTContext *ast_ctx) {
+ if (!m_ast_owned) {
+ m_ast_ap.release();
+ }
+ m_ast_owned = false;
+ m_ast_ap.reset(ast_ctx);
+ GetASTMap().Insert(ast_ctx, this);
}
-void
-ClangASTContext::RemoveExternalSource ()
-{
- ASTContext *ast = getASTContext();
-
- if (ast)
- {
- llvm::IntrusiveRefCntPtr<ExternalASTSource> empty_ast_source_ap;
- ast->setExternalSource (empty_ast_source_ap);
- ast->getTranslationUnitDecl()->setHasExternalLexicalStorage(false);
- //ast->getTranslationUnitDecl()->setHasExternalVisibleStorage(false);
- }
-}
-
-void
-ClangASTContext::setASTContext(clang::ASTContext *ast_ctx)
-{
- if (!m_ast_owned) {
- m_ast_ap.release();
- }
- m_ast_owned = false;
- m_ast_ap.reset(ast_ctx);
- GetASTMap().Insert(ast_ctx, this);
-}
-
-ASTContext *
-ClangASTContext::getASTContext()
-{
- if (m_ast_ap.get() == nullptr)
- {
- m_ast_owned = true;
- m_ast_ap.reset(new ASTContext (*getLanguageOptions(),
- *getSourceManager(),
- *getIdentifierTable(),
- *getSelectorTable(),
- *getBuiltinContext()));
-
- m_ast_ap->getDiagnostics().setClient(getDiagnosticConsumer(), false);
-
- // This can be NULL if we don't know anything about the architecture or if the
- // target for an architecture isn't enabled in the llvm/clang that we built
- TargetInfo *target_info = getTargetInfo();
- if (target_info)
- m_ast_ap->InitBuiltinTypes(*target_info);
-
- if ((m_callback_tag_decl || m_callback_objc_decl) && m_callback_baton)
- {
- m_ast_ap->getTranslationUnitDecl()->setHasExternalLexicalStorage();
- //m_ast_ap->getTranslationUnitDecl()->setHasExternalVisibleStorage();
- }
-
- GetASTMap().Insert(m_ast_ap.get(), this);
+ASTContext *ClangASTContext::getASTContext() {
+ if (m_ast_ap.get() == nullptr) {
+ m_ast_owned = true;
+ m_ast_ap.reset(new ASTContext(*getLanguageOptions(), *getSourceManager(),
+ *getIdentifierTable(), *getSelectorTable(),
+ *getBuiltinContext()));
+
+ m_ast_ap->getDiagnostics().setClient(getDiagnosticConsumer(), false);
- llvm::IntrusiveRefCntPtr<clang::ExternalASTSource> ast_source_ap (new ClangExternalASTSourceCallbacks (ClangASTContext::CompleteTagDecl,
- ClangASTContext::CompleteObjCInterfaceDecl,
- nullptr,
- ClangASTContext::LayoutRecordType,
- this));
- SetExternalSource (ast_source_ap);
+ // This can be NULL if we don't know anything about the architecture or if
+ // the
+ // target for an architecture isn't enabled in the llvm/clang that we built
+ TargetInfo *target_info = getTargetInfo();
+ if (target_info)
+ m_ast_ap->InitBuiltinTypes(*target_info);
+
+ if ((m_callback_tag_decl || m_callback_objc_decl) && m_callback_baton) {
+ m_ast_ap->getTranslationUnitDecl()->setHasExternalLexicalStorage();
+ // m_ast_ap->getTranslationUnitDecl()->setHasExternalVisibleStorage();
}
- return m_ast_ap.get();
+
+ GetASTMap().Insert(m_ast_ap.get(), this);
+
+ llvm::IntrusiveRefCntPtr<clang::ExternalASTSource> ast_source_ap(
+ new ClangExternalASTSourceCallbacks(
+ ClangASTContext::CompleteTagDecl,
+ ClangASTContext::CompleteObjCInterfaceDecl, nullptr,
+ ClangASTContext::LayoutRecordType, this));
+ SetExternalSource(ast_source_ap);
+ }
+ return m_ast_ap.get();
}
-ClangASTContext*
-ClangASTContext::GetASTContext (clang::ASTContext* ast)
-{
- ClangASTContext *clang_ast = GetASTMap().Lookup(ast);
- return clang_ast;
+ClangASTContext *ClangASTContext::GetASTContext(clang::ASTContext *ast) {
+ ClangASTContext *clang_ast = GetASTMap().Lookup(ast);
+ return clang_ast;
}
-Builtin::Context *
-ClangASTContext::getBuiltinContext()
-{
- if (m_builtins_ap.get() == nullptr)
- m_builtins_ap.reset (new Builtin::Context());
- return m_builtins_ap.get();
+Builtin::Context *ClangASTContext::getBuiltinContext() {
+ if (m_builtins_ap.get() == nullptr)
+ m_builtins_ap.reset(new Builtin::Context());
+ return m_builtins_ap.get();
}
-IdentifierTable *
-ClangASTContext::getIdentifierTable()
-{
- if (m_identifier_table_ap.get() == nullptr)
- m_identifier_table_ap.reset(new IdentifierTable (*ClangASTContext::getLanguageOptions(), nullptr));
- return m_identifier_table_ap.get();
+IdentifierTable *ClangASTContext::getIdentifierTable() {
+ if (m_identifier_table_ap.get() == nullptr)
+ m_identifier_table_ap.reset(
+ new IdentifierTable(*ClangASTContext::getLanguageOptions(), nullptr));
+ return m_identifier_table_ap.get();
}
-LangOptions *
-ClangASTContext::getLanguageOptions()
-{
- if (m_language_options_ap.get() == nullptr)
- {
- m_language_options_ap.reset(new LangOptions());
- ParseLangArgs(*m_language_options_ap, IK_ObjCXX, GetTargetTriple());
-// InitializeLangOptions(*m_language_options_ap, IK_ObjCXX);
- }
- return m_language_options_ap.get();
+LangOptions *ClangASTContext::getLanguageOptions() {
+ if (m_language_options_ap.get() == nullptr) {
+ m_language_options_ap.reset(new LangOptions());
+ ParseLangArgs(*m_language_options_ap, IK_ObjCXX, GetTargetTriple());
+ // InitializeLangOptions(*m_language_options_ap, IK_ObjCXX);
+ }
+ return m_language_options_ap.get();
}
-SelectorTable *
-ClangASTContext::getSelectorTable()
-{
- if (m_selector_table_ap.get() == nullptr)
- m_selector_table_ap.reset (new SelectorTable());
- return m_selector_table_ap.get();
+SelectorTable *ClangASTContext::getSelectorTable() {
+ if (m_selector_table_ap.get() == nullptr)
+ m_selector_table_ap.reset(new SelectorTable());
+ return m_selector_table_ap.get();
}
-clang::FileManager *
-ClangASTContext::getFileManager()
-{
- if (m_file_manager_ap.get() == nullptr)
- {
- clang::FileSystemOptions file_system_options;
- m_file_manager_ap.reset(new clang::FileManager(file_system_options));
- }
- return m_file_manager_ap.get();
+clang::FileManager *ClangASTContext::getFileManager() {
+ if (m_file_manager_ap.get() == nullptr) {
+ clang::FileSystemOptions file_system_options;
+ m_file_manager_ap.reset(new clang::FileManager(file_system_options));
+ }
+ return m_file_manager_ap.get();
}
-clang::SourceManager *
-ClangASTContext::getSourceManager()
-{
- if (m_source_manager_ap.get() == nullptr)
- m_source_manager_ap.reset(new clang::SourceManager(*getDiagnosticsEngine(), *getFileManager()));
- return m_source_manager_ap.get();
+clang::SourceManager *ClangASTContext::getSourceManager() {
+ if (m_source_manager_ap.get() == nullptr)
+ m_source_manager_ap.reset(
+ new clang::SourceManager(*getDiagnosticsEngine(), *getFileManager()));
+ return m_source_manager_ap.get();
}
-clang::DiagnosticsEngine *
-ClangASTContext::getDiagnosticsEngine()
-{
- if (m_diagnostics_engine_ap.get() == nullptr)
- {
- llvm::IntrusiveRefCntPtr<DiagnosticIDs> diag_id_sp(new DiagnosticIDs());
- m_diagnostics_engine_ap.reset(new DiagnosticsEngine(diag_id_sp, new DiagnosticOptions()));
- }
- return m_diagnostics_engine_ap.get();
+clang::DiagnosticsEngine *ClangASTContext::getDiagnosticsEngine() {
+ if (m_diagnostics_engine_ap.get() == nullptr) {
+ llvm::IntrusiveRefCntPtr<DiagnosticIDs> diag_id_sp(new DiagnosticIDs());
+ m_diagnostics_engine_ap.reset(
+ new DiagnosticsEngine(diag_id_sp, new DiagnosticOptions()));
+ }
+ return m_diagnostics_engine_ap.get();
}
-clang::MangleContext *
-ClangASTContext::getMangleContext()
-{
- if (m_mangle_ctx_ap.get() == nullptr)
- m_mangle_ctx_ap.reset (getASTContext()->createMangleContext());
- return m_mangle_ctx_ap.get();
+clang::MangleContext *ClangASTContext::getMangleContext() {
+ if (m_mangle_ctx_ap.get() == nullptr)
+ m_mangle_ctx_ap.reset(getASTContext()->createMangleContext());
+ return m_mangle_ctx_ap.get();
}
-class NullDiagnosticConsumer : public DiagnosticConsumer
-{
+class NullDiagnosticConsumer : public DiagnosticConsumer {
public:
- NullDiagnosticConsumer ()
- {
- m_log = lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_EXPRESSIONS);
- }
-
- void
- HandleDiagnostic(DiagnosticsEngine::Level DiagLevel, const clang::Diagnostic &info)
- {
- if (m_log)
- {
- llvm::SmallVector<char, 32> diag_str(10);
- info.FormatDiagnostic(diag_str);
- diag_str.push_back('\0');
- m_log->Printf("Compiler diagnostic: %s\n", diag_str.data());
- }
- }
-
- DiagnosticConsumer *clone (DiagnosticsEngine &Diags) const
- {
- return new NullDiagnosticConsumer ();
+ NullDiagnosticConsumer() {
+ m_log = lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_EXPRESSIONS);
+ }
+
+ void HandleDiagnostic(DiagnosticsEngine::Level DiagLevel,
+ const clang::Diagnostic &info) {
+ if (m_log) {
+ llvm::SmallVector<char, 32> diag_str(10);
+ info.FormatDiagnostic(diag_str);
+ diag_str.push_back('\0');
+ m_log->Printf("Compiler diagnostic: %s\n", diag_str.data());
}
+ }
+
+ DiagnosticConsumer *clone(DiagnosticsEngine &Diags) const {
+ return new NullDiagnosticConsumer();
+ }
+
private:
- Log * m_log;
+ Log *m_log;
};
-DiagnosticConsumer *
-ClangASTContext::getDiagnosticConsumer()
-{
- if (m_diagnostic_consumer_ap.get() == nullptr)
- m_diagnostic_consumer_ap.reset(new NullDiagnosticConsumer);
-
- return m_diagnostic_consumer_ap.get();
-}
+DiagnosticConsumer *ClangASTContext::getDiagnosticConsumer() {
+ if (m_diagnostic_consumer_ap.get() == nullptr)
+ m_diagnostic_consumer_ap.reset(new NullDiagnosticConsumer);
-std::shared_ptr<clang::TargetOptions> &
-ClangASTContext::getTargetOptions() {
- if (m_target_options_rp.get() == nullptr && !m_target_triple.empty())
- {
- m_target_options_rp = std::make_shared<clang::TargetOptions>();
- if (m_target_options_rp.get() != nullptr)
- m_target_options_rp->Triple = m_target_triple;
- }
- return m_target_options_rp;
+ return m_diagnostic_consumer_ap.get();
}
+std::shared_ptr<clang::TargetOptions> &ClangASTContext::getTargetOptions() {
+ if (m_target_options_rp.get() == nullptr && !m_target_triple.empty()) {
+ m_target_options_rp = std::make_shared<clang::TargetOptions>();
+ if (m_target_options_rp.get() != nullptr)
+ m_target_options_rp->Triple = m_target_triple;
+ }
+ return m_target_options_rp;
+}
-TargetInfo *
-ClangASTContext::getTargetInfo()
-{
- // target_triple should be something like "x86_64-apple-macosx"
- if (m_target_info_ap.get() == nullptr && !m_target_triple.empty())
- m_target_info_ap.reset (TargetInfo::CreateTargetInfo(*getDiagnosticsEngine(), getTargetOptions()));
- return m_target_info_ap.get();
+TargetInfo *ClangASTContext::getTargetInfo() {
+ // target_triple should be something like "x86_64-apple-macosx"
+ if (m_target_info_ap.get() == nullptr && !m_target_triple.empty())
+ m_target_info_ap.reset(TargetInfo::CreateTargetInfo(*getDiagnosticsEngine(),
+ getTargetOptions()));
+ return m_target_info_ap.get();
}
#pragma mark Basic Types
-static inline bool
-QualTypeMatchesBitSize(const uint64_t bit_size, ASTContext *ast, QualType qual_type)
-{
- uint64_t qual_type_bit_size = ast->getTypeSize(qual_type);
- if (qual_type_bit_size == bit_size)
- return true;
- return false;
+static inline bool QualTypeMatchesBitSize(const uint64_t bit_size,
+ ASTContext *ast, QualType qual_type) {
+ uint64_t qual_type_bit_size = ast->getTypeSize(qual_type);
+ if (qual_type_bit_size == bit_size)
+ return true;
+ return false;
}
CompilerType
-ClangASTContext::GetBuiltinTypeForEncodingAndBitSize (Encoding encoding, size_t bit_size)
-{
- return ClangASTContext::GetBuiltinTypeForEncodingAndBitSize (getASTContext(), encoding, bit_size);
+ClangASTContext::GetBuiltinTypeForEncodingAndBitSize(Encoding encoding,
+ size_t bit_size) {
+ return ClangASTContext::GetBuiltinTypeForEncodingAndBitSize(
+ getASTContext(), encoding, bit_size);
}
-CompilerType
-ClangASTContext::GetBuiltinTypeForEncodingAndBitSize (ASTContext *ast, Encoding encoding, uint32_t bit_size)
-{
- if (!ast)
- return CompilerType();
- switch (encoding)
- {
- case eEncodingInvalid:
- if (QualTypeMatchesBitSize (bit_size, ast, ast->VoidPtrTy))
- return CompilerType (ast, ast->VoidPtrTy);
- break;
-
- case eEncodingUint:
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedCharTy))
- return CompilerType (ast, ast->UnsignedCharTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedShortTy))
- return CompilerType (ast, ast->UnsignedShortTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedIntTy))
- return CompilerType (ast, ast->UnsignedIntTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedLongTy))
- return CompilerType (ast, ast->UnsignedLongTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedLongLongTy))
- return CompilerType (ast, ast->UnsignedLongLongTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedInt128Ty))
- return CompilerType (ast, ast->UnsignedInt128Ty);
- break;
-
- case eEncodingSint:
- if (QualTypeMatchesBitSize (bit_size, ast, ast->SignedCharTy))
- return CompilerType (ast, ast->SignedCharTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->ShortTy))
- return CompilerType (ast, ast->ShortTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->IntTy))
- return CompilerType (ast, ast->IntTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->LongTy))
- return CompilerType (ast, ast->LongTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->LongLongTy))
- return CompilerType (ast, ast->LongLongTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->Int128Ty))
- return CompilerType (ast, ast->Int128Ty);
- break;
-
- case eEncodingIEEE754:
- if (QualTypeMatchesBitSize (bit_size, ast, ast->FloatTy))
- return CompilerType (ast, ast->FloatTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->DoubleTy))
- return CompilerType (ast, ast->DoubleTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->LongDoubleTy))
- return CompilerType (ast, ast->LongDoubleTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->HalfTy))
- return CompilerType (ast, ast->HalfTy);
- break;
-
- case eEncodingVector:
- // Sanity check that bit_size is a multiple of 8's.
- if (bit_size && !(bit_size & 0x7u))
- return CompilerType (ast, ast->getExtVectorType (ast->UnsignedCharTy, bit_size/8));
- break;
- }
-
+CompilerType ClangASTContext::GetBuiltinTypeForEncodingAndBitSize(
+ ASTContext *ast, Encoding encoding, uint32_t bit_size) {
+ if (!ast)
return CompilerType();
+ switch (encoding) {
+ case eEncodingInvalid:
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->VoidPtrTy))
+ return CompilerType(ast, ast->VoidPtrTy);
+ break;
+
+ case eEncodingUint:
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedCharTy))
+ return CompilerType(ast, ast->UnsignedCharTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedShortTy))
+ return CompilerType(ast, ast->UnsignedShortTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedIntTy))
+ return CompilerType(ast, ast->UnsignedIntTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedLongTy))
+ return CompilerType(ast, ast->UnsignedLongTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedLongLongTy))
+ return CompilerType(ast, ast->UnsignedLongLongTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedInt128Ty))
+ return CompilerType(ast, ast->UnsignedInt128Ty);
+ break;
+
+ case eEncodingSint:
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->SignedCharTy))
+ return CompilerType(ast, ast->SignedCharTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->ShortTy))
+ return CompilerType(ast, ast->ShortTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->IntTy))
+ return CompilerType(ast, ast->IntTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->LongTy))
+ return CompilerType(ast, ast->LongTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->LongLongTy))
+ return CompilerType(ast, ast->LongLongTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->Int128Ty))
+ return CompilerType(ast, ast->Int128Ty);
+ break;
+
+ case eEncodingIEEE754:
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->FloatTy))
+ return CompilerType(ast, ast->FloatTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->DoubleTy))
+ return CompilerType(ast, ast->DoubleTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->LongDoubleTy))
+ return CompilerType(ast, ast->LongDoubleTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->HalfTy))
+ return CompilerType(ast, ast->HalfTy);
+ break;
+
+ case eEncodingVector:
+ // Sanity check that bit_size is a multiple of 8's.
+ if (bit_size && !(bit_size & 0x7u))
+ return CompilerType(
+ ast, ast->getExtVectorType(ast->UnsignedCharTy, bit_size / 8));
+ break;
+ }
+
+ return CompilerType();
}
-
-
lldb::BasicType
-ClangASTContext::GetBasicTypeEnumeration (const ConstString &name)
-{
- if (name)
- {
- typedef UniqueCStringMap<lldb::BasicType> TypeNameToBasicTypeMap;
- static TypeNameToBasicTypeMap g_type_map;
- static std::once_flag g_once_flag;
- std::call_once(g_once_flag, [](){
- // "void"
- g_type_map.Append(ConstString("void").GetCString(), eBasicTypeVoid);
-
- // "char"
- g_type_map.Append(ConstString("char").GetCString(), eBasicTypeChar);
- g_type_map.Append(ConstString("signed char").GetCString(), eBasicTypeSignedChar);
- g_type_map.Append(ConstString("unsigned char").GetCString(), eBasicTypeUnsignedChar);
- g_type_map.Append(ConstString("wchar_t").GetCString(), eBasicTypeWChar);
- g_type_map.Append(ConstString("signed wchar_t").GetCString(), eBasicTypeSignedWChar);
- g_type_map.Append(ConstString("unsigned wchar_t").GetCString(), eBasicTypeUnsignedWChar);
- // "short"
- g_type_map.Append(ConstString("short").GetCString(), eBasicTypeShort);
- g_type_map.Append(ConstString("short int").GetCString(), eBasicTypeShort);
- g_type_map.Append(ConstString("unsigned short").GetCString(), eBasicTypeUnsignedShort);
- g_type_map.Append(ConstString("unsigned short int").GetCString(), eBasicTypeUnsignedShort);
-
- // "int"
- g_type_map.Append(ConstString("int").GetCString(), eBasicTypeInt);
- g_type_map.Append(ConstString("signed int").GetCString(), eBasicTypeInt);
- g_type_map.Append(ConstString("unsigned int").GetCString(), eBasicTypeUnsignedInt);
- g_type_map.Append(ConstString("unsigned").GetCString(), eBasicTypeUnsignedInt);
-
- // "long"
- g_type_map.Append(ConstString("long").GetCString(), eBasicTypeLong);
- g_type_map.Append(ConstString("long int").GetCString(), eBasicTypeLong);
- g_type_map.Append(ConstString("unsigned long").GetCString(), eBasicTypeUnsignedLong);
- g_type_map.Append(ConstString("unsigned long int").GetCString(), eBasicTypeUnsignedLong);
-
- // "long long"
- g_type_map.Append(ConstString("long long").GetCString(), eBasicTypeLongLong);
- g_type_map.Append(ConstString("long long int").GetCString(), eBasicTypeLongLong);
- g_type_map.Append(ConstString("unsigned long long").GetCString(), eBasicTypeUnsignedLongLong);
- g_type_map.Append(ConstString("unsigned long long int").GetCString(), eBasicTypeUnsignedLongLong);
-
- // "int128"
- g_type_map.Append(ConstString("__int128_t").GetCString(), eBasicTypeInt128);
- g_type_map.Append(ConstString("__uint128_t").GetCString(), eBasicTypeUnsignedInt128);
-
- // Miscellaneous
- g_type_map.Append(ConstString("bool").GetCString(), eBasicTypeBool);
- g_type_map.Append(ConstString("float").GetCString(), eBasicTypeFloat);
- g_type_map.Append(ConstString("double").GetCString(), eBasicTypeDouble);
- g_type_map.Append(ConstString("long double").GetCString(), eBasicTypeLongDouble);
- g_type_map.Append(ConstString("id").GetCString(), eBasicTypeObjCID);
- g_type_map.Append(ConstString("SEL").GetCString(), eBasicTypeObjCSel);
- g_type_map.Append(ConstString("nullptr").GetCString(), eBasicTypeNullPtr);
- g_type_map.Sort();
- });
-
- return g_type_map.Find(name.GetCString(), eBasicTypeInvalid);
- }
- return eBasicTypeInvalid;
-}
+ClangASTContext::GetBasicTypeEnumeration(const ConstString &name) {
+ if (name) {
+ typedef UniqueCStringMap<lldb::BasicType> TypeNameToBasicTypeMap;
+ static TypeNameToBasicTypeMap g_type_map;
+ static std::once_flag g_once_flag;
+ std::call_once(g_once_flag, []() {
+ // "void"
+ g_type_map.Append(ConstString("void").GetCString(), eBasicTypeVoid);
+
+ // "char"
+ g_type_map.Append(ConstString("char").GetCString(), eBasicTypeChar);
+ g_type_map.Append(ConstString("signed char").GetCString(),
+ eBasicTypeSignedChar);
+ g_type_map.Append(ConstString("unsigned char").GetCString(),
+ eBasicTypeUnsignedChar);
+ g_type_map.Append(ConstString("wchar_t").GetCString(), eBasicTypeWChar);
+ g_type_map.Append(ConstString("signed wchar_t").GetCString(),
+ eBasicTypeSignedWChar);
+ g_type_map.Append(ConstString("unsigned wchar_t").GetCString(),
+ eBasicTypeUnsignedWChar);
+ // "short"
+ g_type_map.Append(ConstString("short").GetCString(), eBasicTypeShort);
+ g_type_map.Append(ConstString("short int").GetCString(), eBasicTypeShort);
+ g_type_map.Append(ConstString("unsigned short").GetCString(),
+ eBasicTypeUnsignedShort);
+ g_type_map.Append(ConstString("unsigned short int").GetCString(),
+ eBasicTypeUnsignedShort);
+
+ // "int"
+ g_type_map.Append(ConstString("int").GetCString(), eBasicTypeInt);
+ g_type_map.Append(ConstString("signed int").GetCString(), eBasicTypeInt);
+ g_type_map.Append(ConstString("unsigned int").GetCString(),
+ eBasicTypeUnsignedInt);
+ g_type_map.Append(ConstString("unsigned").GetCString(),
+ eBasicTypeUnsignedInt);
+
+ // "long"
+ g_type_map.Append(ConstString("long").GetCString(), eBasicTypeLong);
+ g_type_map.Append(ConstString("long int").GetCString(), eBasicTypeLong);
+ g_type_map.Append(ConstString("unsigned long").GetCString(),
+ eBasicTypeUnsignedLong);
+ g_type_map.Append(ConstString("unsigned long int").GetCString(),
+ eBasicTypeUnsignedLong);
+
+ // "long long"
+ g_type_map.Append(ConstString("long long").GetCString(),
+ eBasicTypeLongLong);
+ g_type_map.Append(ConstString("long long int").GetCString(),
+ eBasicTypeLongLong);
+ g_type_map.Append(ConstString("unsigned long long").GetCString(),
+ eBasicTypeUnsignedLongLong);
+ g_type_map.Append(ConstString("unsigned long long int").GetCString(),
+ eBasicTypeUnsignedLongLong);
+
+ // "int128"
+ g_type_map.Append(ConstString("__int128_t").GetCString(),
+ eBasicTypeInt128);
+ g_type_map.Append(ConstString("__uint128_t").GetCString(),
+ eBasicTypeUnsignedInt128);
+
+ // Miscellaneous
+ g_type_map.Append(ConstString("bool").GetCString(), eBasicTypeBool);
+ g_type_map.Append(ConstString("float").GetCString(), eBasicTypeFloat);
+ g_type_map.Append(ConstString("double").GetCString(), eBasicTypeDouble);
+ g_type_map.Append(ConstString("long double").GetCString(),
+ eBasicTypeLongDouble);
+ g_type_map.Append(ConstString("id").GetCString(), eBasicTypeObjCID);
+ g_type_map.Append(ConstString("SEL").GetCString(), eBasicTypeObjCSel);
+ g_type_map.Append(ConstString("nullptr").GetCString(), eBasicTypeNullPtr);
+ g_type_map.Sort();
+ });
-CompilerType
-ClangASTContext::GetBasicType (ASTContext *ast, const ConstString &name)
-{
- if (ast)
- {
- lldb::BasicType basic_type = ClangASTContext::GetBasicTypeEnumeration (name);
- return ClangASTContext::GetBasicType (ast, basic_type);
- }
- return CompilerType();
+ return g_type_map.Find(name.GetCString(), eBasicTypeInvalid);
+ }
+ return eBasicTypeInvalid;
}
-uint32_t
-ClangASTContext::GetPointerByteSize ()
-{
- if (m_pointer_byte_size == 0)
- m_pointer_byte_size = GetBasicType(lldb::eBasicTypeVoid).GetPointerType().GetByteSize(nullptr);
- return m_pointer_byte_size;
+CompilerType ClangASTContext::GetBasicType(ASTContext *ast,
+ const ConstString &name) {
+ if (ast) {
+ lldb::BasicType basic_type = ClangASTContext::GetBasicTypeEnumeration(name);
+ return ClangASTContext::GetBasicType(ast, basic_type);
+ }
+ return CompilerType();
}
-CompilerType
-ClangASTContext::GetBasicType (lldb::BasicType basic_type)
-{
- return GetBasicType (getASTContext(), basic_type);
+uint32_t ClangASTContext::GetPointerByteSize() {
+ if (m_pointer_byte_size == 0)
+ m_pointer_byte_size = GetBasicType(lldb::eBasicTypeVoid)
+ .GetPointerType()
+ .GetByteSize(nullptr);
+ return m_pointer_byte_size;
}
-CompilerType
-ClangASTContext::GetBasicType (ASTContext *ast, lldb::BasicType basic_type)
-{
- if (!ast)
- return CompilerType();
- lldb::opaque_compiler_type_t clang_type = GetOpaqueCompilerType(ast, basic_type);
-
- if (clang_type)
- return CompilerType(GetASTContext(ast), clang_type);
- return CompilerType();
+CompilerType ClangASTContext::GetBasicType(lldb::BasicType basic_type) {
+ return GetBasicType(getASTContext(), basic_type);
}
+CompilerType ClangASTContext::GetBasicType(ASTContext *ast,
+ lldb::BasicType basic_type) {
+ if (!ast)
+ return CompilerType();
+ lldb::opaque_compiler_type_t clang_type =
+ GetOpaqueCompilerType(ast, basic_type);
-CompilerType
-ClangASTContext::GetBuiltinTypeForDWARFEncodingAndBitSize (const char *type_name, uint32_t dw_ate, uint32_t bit_size)
-{
- ASTContext *ast = getASTContext();
-
-#define streq(a,b) strcmp(a,b) == 0
- assert (ast != nullptr);
- if (ast)
- {
- switch (dw_ate)
- {
- default:
- break;
-
- case DW_ATE_address:
- if (QualTypeMatchesBitSize (bit_size, ast, ast->VoidPtrTy))
- return CompilerType (ast, ast->VoidPtrTy);
- break;
-
- case DW_ATE_boolean:
- if (QualTypeMatchesBitSize (bit_size, ast, ast->BoolTy))
- return CompilerType (ast, ast->BoolTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedCharTy))
- return CompilerType (ast, ast->UnsignedCharTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedShortTy))
- return CompilerType (ast, ast->UnsignedShortTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedIntTy))
- return CompilerType (ast, ast->UnsignedIntTy);
- break;
-
- case DW_ATE_lo_user:
- // This has been seen to mean DW_AT_complex_integer
- if (type_name)
- {
- if (::strstr(type_name, "complex"))
- {
- CompilerType complex_int_clang_type = GetBuiltinTypeForDWARFEncodingAndBitSize ("int", DW_ATE_signed, bit_size/2);
- return CompilerType(ast, ast->getComplexType(ClangUtil::GetQualType(complex_int_clang_type)));
- }
- }
- break;
-
- case DW_ATE_complex_float:
- if (QualTypeMatchesBitSize (bit_size, ast, ast->FloatComplexTy))
- return CompilerType (ast, ast->FloatComplexTy);
- else if (QualTypeMatchesBitSize (bit_size, ast, ast->DoubleComplexTy))
- return CompilerType (ast, ast->DoubleComplexTy);
- else if (QualTypeMatchesBitSize (bit_size, ast, ast->LongDoubleComplexTy))
- return CompilerType (ast, ast->LongDoubleComplexTy);
- else
- {
- CompilerType complex_float_clang_type = GetBuiltinTypeForDWARFEncodingAndBitSize ("float", DW_ATE_float, bit_size/2);
- return CompilerType(ast, ast->getComplexType(ClangUtil::GetQualType(complex_float_clang_type)));
- }
- break;
-
- case DW_ATE_float:
- if (streq(type_name, "float") && QualTypeMatchesBitSize (bit_size, ast, ast->FloatTy))
- return CompilerType (ast, ast->FloatTy);
- if (streq(type_name, "double") && QualTypeMatchesBitSize (bit_size, ast, ast->DoubleTy))
- return CompilerType (ast, ast->DoubleTy);
- if (streq(type_name, "long double") && QualTypeMatchesBitSize (bit_size, ast, ast->LongDoubleTy))
- return CompilerType (ast, ast->LongDoubleTy);
- // Fall back to not requiring a name match
- if (QualTypeMatchesBitSize (bit_size, ast, ast->FloatTy))
- return CompilerType (ast, ast->FloatTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->DoubleTy))
- return CompilerType (ast, ast->DoubleTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->LongDoubleTy))
- return CompilerType (ast, ast->LongDoubleTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->HalfTy))
- return CompilerType (ast, ast->HalfTy);
- break;
-
- case DW_ATE_signed:
- if (type_name)
- {
- if (streq(type_name, "wchar_t") &&
- QualTypeMatchesBitSize (bit_size, ast, ast->WCharTy) &&
- (getTargetInfo() && TargetInfo::isTypeSigned (getTargetInfo()->getWCharType())))
- return CompilerType (ast, ast->WCharTy);
- if (streq(type_name, "void") &&
- QualTypeMatchesBitSize (bit_size, ast, ast->VoidTy))
- return CompilerType (ast, ast->VoidTy);
- if (strstr(type_name, "long long") &&
- QualTypeMatchesBitSize (bit_size, ast, ast->LongLongTy))
- return CompilerType (ast, ast->LongLongTy);
- if (strstr(type_name, "long") &&
- QualTypeMatchesBitSize (bit_size, ast, ast->LongTy))
- return CompilerType (ast, ast->LongTy);
- if (strstr(type_name, "short") &&
- QualTypeMatchesBitSize (bit_size, ast, ast->ShortTy))
- return CompilerType (ast, ast->ShortTy);
- if (strstr(type_name, "char"))
- {
- if (QualTypeMatchesBitSize (bit_size, ast, ast->CharTy))
- return CompilerType (ast, ast->CharTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->SignedCharTy))
- return CompilerType (ast, ast->SignedCharTy);
- }
- if (strstr(type_name, "int"))
- {
- if (QualTypeMatchesBitSize (bit_size, ast, ast->IntTy))
- return CompilerType (ast, ast->IntTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->Int128Ty))
- return CompilerType (ast, ast->Int128Ty);
- }
- }
- // We weren't able to match up a type name, just search by size
- if (QualTypeMatchesBitSize (bit_size, ast, ast->CharTy))
- return CompilerType (ast, ast->CharTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->ShortTy))
- return CompilerType (ast, ast->ShortTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->IntTy))
- return CompilerType (ast, ast->IntTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->LongTy))
- return CompilerType (ast, ast->LongTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->LongLongTy))
- return CompilerType (ast, ast->LongLongTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->Int128Ty))
- return CompilerType (ast, ast->Int128Ty);
- break;
+ if (clang_type)
+ return CompilerType(GetASTContext(ast), clang_type);
+ return CompilerType();
+}
- case DW_ATE_signed_char:
- if (ast->getLangOpts().CharIsSigned && type_name && streq(type_name, "char"))
- {
- if (QualTypeMatchesBitSize (bit_size, ast, ast->CharTy))
- return CompilerType (ast, ast->CharTy);
- }
- if (QualTypeMatchesBitSize (bit_size, ast, ast->SignedCharTy))
- return CompilerType (ast, ast->SignedCharTy);
- break;
-
- case DW_ATE_unsigned:
- if (type_name)
- {
- if (streq(type_name, "wchar_t"))
- {
- if (QualTypeMatchesBitSize (bit_size, ast, ast->WCharTy))
- {
- if (!(getTargetInfo() && TargetInfo::isTypeSigned (getTargetInfo()->getWCharType())))
- return CompilerType (ast, ast->WCharTy);
- }
- }
- if (strstr(type_name, "long long"))
- {
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedLongLongTy))
- return CompilerType (ast, ast->UnsignedLongLongTy);
- }
- else if (strstr(type_name, "long"))
- {
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedLongTy))
- return CompilerType (ast, ast->UnsignedLongTy);
- }
- else if (strstr(type_name, "short"))
- {
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedShortTy))
- return CompilerType (ast, ast->UnsignedShortTy);
- }
- else if (strstr(type_name, "char"))
- {
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedCharTy))
- return CompilerType (ast, ast->UnsignedCharTy);
- }
- else if (strstr(type_name, "int"))
- {
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedIntTy))
- return CompilerType (ast, ast->UnsignedIntTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedInt128Ty))
- return CompilerType (ast, ast->UnsignedInt128Ty);
- }
- }
- // We weren't able to match up a type name, just search by size
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedCharTy))
- return CompilerType (ast, ast->UnsignedCharTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedShortTy))
- return CompilerType (ast, ast->UnsignedShortTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedIntTy))
- return CompilerType (ast, ast->UnsignedIntTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedLongTy))
- return CompilerType (ast, ast->UnsignedLongTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedLongLongTy))
- return CompilerType (ast, ast->UnsignedLongLongTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedInt128Ty))
- return CompilerType (ast, ast->UnsignedInt128Ty);
- break;
+CompilerType ClangASTContext::GetBuiltinTypeForDWARFEncodingAndBitSize(
+ const char *type_name, uint32_t dw_ate, uint32_t bit_size) {
+ ASTContext *ast = getASTContext();
- case DW_ATE_unsigned_char:
- if (!ast->getLangOpts().CharIsSigned && type_name && streq(type_name, "char"))
- {
- if (QualTypeMatchesBitSize (bit_size, ast, ast->CharTy))
- return CompilerType (ast, ast->CharTy);
- }
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedCharTy))
- return CompilerType (ast, ast->UnsignedCharTy);
- if (QualTypeMatchesBitSize (bit_size, ast, ast->UnsignedShortTy))
- return CompilerType (ast, ast->UnsignedShortTy);
- break;
-
- case DW_ATE_imaginary_float:
- break;
-
- case DW_ATE_UTF:
- if (type_name)
- {
- if (streq(type_name, "char16_t"))
- {
- return CompilerType (ast, ast->Char16Ty);
- }
- else if (streq(type_name, "char32_t"))
- {
- return CompilerType (ast, ast->Char32Ty);
- }
- }
- break;
+#define streq(a, b) strcmp(a, b) == 0
+ assert(ast != nullptr);
+ if (ast) {
+ switch (dw_ate) {
+ default:
+ break;
+
+ case DW_ATE_address:
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->VoidPtrTy))
+ return CompilerType(ast, ast->VoidPtrTy);
+ break;
+
+ case DW_ATE_boolean:
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->BoolTy))
+ return CompilerType(ast, ast->BoolTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedCharTy))
+ return CompilerType(ast, ast->UnsignedCharTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedShortTy))
+ return CompilerType(ast, ast->UnsignedShortTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedIntTy))
+ return CompilerType(ast, ast->UnsignedIntTy);
+ break;
+
+ case DW_ATE_lo_user:
+ // This has been seen to mean DW_AT_complex_integer
+ if (type_name) {
+ if (::strstr(type_name, "complex")) {
+ CompilerType complex_int_clang_type =
+ GetBuiltinTypeForDWARFEncodingAndBitSize("int", DW_ATE_signed,
+ bit_size / 2);
+ return CompilerType(ast, ast->getComplexType(ClangUtil::GetQualType(
+ complex_int_clang_type)));
}
+ }
+ break;
+
+ case DW_ATE_complex_float:
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->FloatComplexTy))
+ return CompilerType(ast, ast->FloatComplexTy);
+ else if (QualTypeMatchesBitSize(bit_size, ast, ast->DoubleComplexTy))
+ return CompilerType(ast, ast->DoubleComplexTy);
+ else if (QualTypeMatchesBitSize(bit_size, ast, ast->LongDoubleComplexTy))
+ return CompilerType(ast, ast->LongDoubleComplexTy);
+ else {
+ CompilerType complex_float_clang_type =
+ GetBuiltinTypeForDWARFEncodingAndBitSize("float", DW_ATE_float,
+ bit_size / 2);
+ return CompilerType(ast, ast->getComplexType(ClangUtil::GetQualType(
+ complex_float_clang_type)));
+ }
+ break;
+
+ case DW_ATE_float:
+ if (streq(type_name, "float") &&
+ QualTypeMatchesBitSize(bit_size, ast, ast->FloatTy))
+ return CompilerType(ast, ast->FloatTy);
+ if (streq(type_name, "double") &&
+ QualTypeMatchesBitSize(bit_size, ast, ast->DoubleTy))
+ return CompilerType(ast, ast->DoubleTy);
+ if (streq(type_name, "long double") &&
+ QualTypeMatchesBitSize(bit_size, ast, ast->LongDoubleTy))
+ return CompilerType(ast, ast->LongDoubleTy);
+ // Fall back to not requiring a name match
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->FloatTy))
+ return CompilerType(ast, ast->FloatTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->DoubleTy))
+ return CompilerType(ast, ast->DoubleTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->LongDoubleTy))
+ return CompilerType(ast, ast->LongDoubleTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->HalfTy))
+ return CompilerType(ast, ast->HalfTy);
+ break;
+
+ case DW_ATE_signed:
+ if (type_name) {
+ if (streq(type_name, "wchar_t") &&
+ QualTypeMatchesBitSize(bit_size, ast, ast->WCharTy) &&
+ (getTargetInfo() &&
+ TargetInfo::isTypeSigned(getTargetInfo()->getWCharType())))
+ return CompilerType(ast, ast->WCharTy);
+ if (streq(type_name, "void") &&
+ QualTypeMatchesBitSize(bit_size, ast, ast->VoidTy))
+ return CompilerType(ast, ast->VoidTy);
+ if (strstr(type_name, "long long") &&
+ QualTypeMatchesBitSize(bit_size, ast, ast->LongLongTy))
+ return CompilerType(ast, ast->LongLongTy);
+ if (strstr(type_name, "long") &&
+ QualTypeMatchesBitSize(bit_size, ast, ast->LongTy))
+ return CompilerType(ast, ast->LongTy);
+ if (strstr(type_name, "short") &&
+ QualTypeMatchesBitSize(bit_size, ast, ast->ShortTy))
+ return CompilerType(ast, ast->ShortTy);
+ if (strstr(type_name, "char")) {
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->CharTy))
+ return CompilerType(ast, ast->CharTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->SignedCharTy))
+ return CompilerType(ast, ast->SignedCharTy);
+ }
+ if (strstr(type_name, "int")) {
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->IntTy))
+ return CompilerType(ast, ast->IntTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->Int128Ty))
+ return CompilerType(ast, ast->Int128Ty);
+ }
+ }
+ // We weren't able to match up a type name, just search by size
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->CharTy))
+ return CompilerType(ast, ast->CharTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->ShortTy))
+ return CompilerType(ast, ast->ShortTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->IntTy))
+ return CompilerType(ast, ast->IntTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->LongTy))
+ return CompilerType(ast, ast->LongTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->LongLongTy))
+ return CompilerType(ast, ast->LongLongTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->Int128Ty))
+ return CompilerType(ast, ast->Int128Ty);
+ break;
+
+ case DW_ATE_signed_char:
+ if (ast->getLangOpts().CharIsSigned && type_name &&
+ streq(type_name, "char")) {
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->CharTy))
+ return CompilerType(ast, ast->CharTy);
+ }
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->SignedCharTy))
+ return CompilerType(ast, ast->SignedCharTy);
+ break;
+
+ case DW_ATE_unsigned:
+ if (type_name) {
+ if (streq(type_name, "wchar_t")) {
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->WCharTy)) {
+ if (!(getTargetInfo() &&
+ TargetInfo::isTypeSigned(getTargetInfo()->getWCharType())))
+ return CompilerType(ast, ast->WCharTy);
+ }
+ }
+ if (strstr(type_name, "long long")) {
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedLongLongTy))
+ return CompilerType(ast, ast->UnsignedLongLongTy);
+ } else if (strstr(type_name, "long")) {
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedLongTy))
+ return CompilerType(ast, ast->UnsignedLongTy);
+ } else if (strstr(type_name, "short")) {
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedShortTy))
+ return CompilerType(ast, ast->UnsignedShortTy);
+ } else if (strstr(type_name, "char")) {
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedCharTy))
+ return CompilerType(ast, ast->UnsignedCharTy);
+ } else if (strstr(type_name, "int")) {
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedIntTy))
+ return CompilerType(ast, ast->UnsignedIntTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedInt128Ty))
+ return CompilerType(ast, ast->UnsignedInt128Ty);
+ }
+ }
+ // We weren't able to match up a type name, just search by size
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedCharTy))
+ return CompilerType(ast, ast->UnsignedCharTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedShortTy))
+ return CompilerType(ast, ast->UnsignedShortTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedIntTy))
+ return CompilerType(ast, ast->UnsignedIntTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedLongTy))
+ return CompilerType(ast, ast->UnsignedLongTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedLongLongTy))
+ return CompilerType(ast, ast->UnsignedLongLongTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedInt128Ty))
+ return CompilerType(ast, ast->UnsignedInt128Ty);
+ break;
+
+ case DW_ATE_unsigned_char:
+ if (!ast->getLangOpts().CharIsSigned && type_name &&
+ streq(type_name, "char")) {
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->CharTy))
+ return CompilerType(ast, ast->CharTy);
+ }
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedCharTy))
+ return CompilerType(ast, ast->UnsignedCharTy);
+ if (QualTypeMatchesBitSize(bit_size, ast, ast->UnsignedShortTy))
+ return CompilerType(ast, ast->UnsignedShortTy);
+ break;
+
+ case DW_ATE_imaginary_float:
+ break;
+
+ case DW_ATE_UTF:
+ if (type_name) {
+ if (streq(type_name, "char16_t")) {
+ return CompilerType(ast, ast->Char16Ty);
+ } else if (streq(type_name, "char32_t")) {
+ return CompilerType(ast, ast->Char32Ty);
+ }
+ }
+ break;
}
- // This assert should fire for anything that we don't catch above so we know
- // to fix any issues we run into.
- if (type_name)
- {
- Host::SystemLog (Host::eSystemLogError, "error: need to add support for DW_TAG_base_type '%s' encoded with DW_ATE = 0x%x, bit_size = %u\n", type_name, dw_ate, bit_size);
- }
- else
- {
- Host::SystemLog (Host::eSystemLogError, "error: need to add support for DW_TAG_base_type encoded with DW_ATE = 0x%x, bit_size = %u\n", dw_ate, bit_size);
- }
- return CompilerType ();
+ }
+ // This assert should fire for anything that we don't catch above so we know
+ // to fix any issues we run into.
+ if (type_name) {
+ Host::SystemLog(Host::eSystemLogError, "error: need to add support for "
+ "DW_TAG_base_type '%s' encoded with "
+ "DW_ATE = 0x%x, bit_size = %u\n",
+ type_name, dw_ate, bit_size);
+ } else {
+ Host::SystemLog(Host::eSystemLogError, "error: need to add support for "
+ "DW_TAG_base_type encoded with "
+ "DW_ATE = 0x%x, bit_size = %u\n",
+ dw_ate, bit_size);
+ }
+ return CompilerType();
}
-CompilerType
-ClangASTContext::GetUnknownAnyType(clang::ASTContext *ast)
-{
- if (ast)
- return CompilerType (ast, ast->UnknownAnyTy);
- return CompilerType();
+CompilerType ClangASTContext::GetUnknownAnyType(clang::ASTContext *ast) {
+ if (ast)
+ return CompilerType(ast, ast->UnknownAnyTy);
+ return CompilerType();
}
-CompilerType
-ClangASTContext::GetCStringType (bool is_const)
-{
- ASTContext *ast = getASTContext();
- QualType char_type(ast->CharTy);
-
- if (is_const)
- char_type.addConst();
-
- return CompilerType (ast, ast->getPointerType(char_type));
+CompilerType ClangASTContext::GetCStringType(bool is_const) {
+ ASTContext *ast = getASTContext();
+ QualType char_type(ast->CharTy);
+
+ if (is_const)
+ char_type.addConst();
+
+ return CompilerType(ast, ast->getPointerType(char_type));
}
clang::DeclContext *
-ClangASTContext::GetTranslationUnitDecl (clang::ASTContext *ast)
-{
- return ast->getTranslationUnitDecl();
-}
-
-clang::Decl *
-ClangASTContext::CopyDecl (ASTContext *dst_ast,
- ASTContext *src_ast,
- clang::Decl *source_decl)
-{
- FileSystemOptions file_system_options;
- FileManager file_manager (file_system_options);
- ASTImporter importer(*dst_ast, file_manager,
- *src_ast, file_manager,
- false);
-
- return importer.Import(source_decl);
-}
-
-bool
-ClangASTContext::AreTypesSame (CompilerType type1,
- CompilerType type2,
- bool ignore_qualifiers)
-{
- ClangASTContext *ast = llvm::dyn_cast_or_null<ClangASTContext>(type1.GetTypeSystem());
- if (!ast || ast != type2.GetTypeSystem())
- return false;
-
- if (type1.GetOpaqueQualType() == type2.GetOpaqueQualType())
- return true;
+ClangASTContext::GetTranslationUnitDecl(clang::ASTContext *ast) {
+ return ast->getTranslationUnitDecl();
+}
- QualType type1_qual = ClangUtil::GetQualType(type1);
- QualType type2_qual = ClangUtil::GetQualType(type2);
+clang::Decl *ClangASTContext::CopyDecl(ASTContext *dst_ast, ASTContext *src_ast,
+ clang::Decl *source_decl) {
+ FileSystemOptions file_system_options;
+ FileManager file_manager(file_system_options);
+ ASTImporter importer(*dst_ast, file_manager, *src_ast, file_manager, false);
- if (ignore_qualifiers)
- {
- type1_qual = type1_qual.getUnqualifiedType();
- type2_qual = type2_qual.getUnqualifiedType();
- }
-
- return ast->getASTContext()->hasSameType (type1_qual, type2_qual);
+ return importer.Import(source_decl);
}
-CompilerType
-ClangASTContext::GetTypeForDecl (clang::NamedDecl *decl)
-{
- if (clang::ObjCInterfaceDecl *interface_decl = llvm::dyn_cast<clang::ObjCInterfaceDecl>(decl))
- return GetTypeForDecl(interface_decl);
- if (clang::TagDecl *tag_decl = llvm::dyn_cast<clang::TagDecl>(decl))
- return GetTypeForDecl(tag_decl);
- return CompilerType();
+bool ClangASTContext::AreTypesSame(CompilerType type1, CompilerType type2,
+ bool ignore_qualifiers) {
+ ClangASTContext *ast =
+ llvm::dyn_cast_or_null<ClangASTContext>(type1.GetTypeSystem());
+ if (!ast || ast != type2.GetTypeSystem())
+ return false;
+
+ if (type1.GetOpaqueQualType() == type2.GetOpaqueQualType())
+ return true;
+
+ QualType type1_qual = ClangUtil::GetQualType(type1);
+ QualType type2_qual = ClangUtil::GetQualType(type2);
+
+ if (ignore_qualifiers) {
+ type1_qual = type1_qual.getUnqualifiedType();
+ type2_qual = type2_qual.getUnqualifiedType();
+ }
+
+ return ast->getASTContext()->hasSameType(type1_qual, type2_qual);
}
+CompilerType ClangASTContext::GetTypeForDecl(clang::NamedDecl *decl) {
+ if (clang::ObjCInterfaceDecl *interface_decl =
+ llvm::dyn_cast<clang::ObjCInterfaceDecl>(decl))
+ return GetTypeForDecl(interface_decl);
+ if (clang::TagDecl *tag_decl = llvm::dyn_cast<clang::TagDecl>(decl))
+ return GetTypeForDecl(tag_decl);
+ return CompilerType();
+}
-CompilerType
-ClangASTContext::GetTypeForDecl (TagDecl *decl)
-{
- // No need to call the getASTContext() accessor (which can create the AST
- // if it isn't created yet, because we can't have created a decl in this
- // AST if our AST didn't already exist...
- ASTContext *ast = &decl->getASTContext();
- if (ast)
- return CompilerType (ast, ast->getTagDeclType(decl));
- return CompilerType();
+CompilerType ClangASTContext::GetTypeForDecl(TagDecl *decl) {
+ // No need to call the getASTContext() accessor (which can create the AST
+ // if it isn't created yet, because we can't have created a decl in this
+ // AST if our AST didn't already exist...
+ ASTContext *ast = &decl->getASTContext();
+ if (ast)
+ return CompilerType(ast, ast->getTagDeclType(decl));
+ return CompilerType();
}
-CompilerType
-ClangASTContext::GetTypeForDecl (ObjCInterfaceDecl *decl)
-{
- // No need to call the getASTContext() accessor (which can create the AST
- // if it isn't created yet, because we can't have created a decl in this
- // AST if our AST didn't already exist...
- ASTContext *ast = &decl->getASTContext();
- if (ast)
- return CompilerType (ast, ast->getObjCInterfaceType(decl));
- return CompilerType();
+CompilerType ClangASTContext::GetTypeForDecl(ObjCInterfaceDecl *decl) {
+ // No need to call the getASTContext() accessor (which can create the AST
+ // if it isn't created yet, because we can't have created a decl in this
+ // AST if our AST didn't already exist...
+ ASTContext *ast = &decl->getASTContext();
+ if (ast)
+ return CompilerType(ast, ast->getObjCInterfaceType(decl));
+ return CompilerType();
}
#pragma mark Structure, Unions, Classes
-CompilerType
-ClangASTContext::CreateRecordType (DeclContext *decl_ctx,
- AccessType access_type,
- const char *name,
- int kind,
- LanguageType language,
- ClangASTMetadata *metadata)
-{
- ASTContext *ast = getASTContext();
- assert (ast != nullptr);
-
- if (decl_ctx == nullptr)
- decl_ctx = ast->getTranslationUnitDecl();
-
-
- if (language == eLanguageTypeObjC || language == eLanguageTypeObjC_plus_plus)
- {
- bool isForwardDecl = true;
- bool isInternal = false;
- return CreateObjCClass (name, decl_ctx, isForwardDecl, isInternal, metadata);
- }
-
- // NOTE: Eventually CXXRecordDecl will be merged back into RecordDecl and
- // we will need to update this code. I was told to currently always use
- // the CXXRecordDecl class since we often don't know from debug information
- // if something is struct or a class, so we default to always use the more
- // complete definition just in case.
-
- bool is_anonymous = (!name) || (!name[0]);
-
- CXXRecordDecl *decl = CXXRecordDecl::Create (*ast,
- (TagDecl::TagKind)kind,
- decl_ctx,
- SourceLocation(),
- SourceLocation(),
- is_anonymous ? nullptr : &ast->Idents.get(name));
-
- if (is_anonymous)
- decl->setAnonymousStructOrUnion(true);
-
- if (decl)
- {
- if (metadata)
- SetMetadata(ast, decl, *metadata);
+CompilerType ClangASTContext::CreateRecordType(DeclContext *decl_ctx,
+ AccessType access_type,
+ const char *name, int kind,
+ LanguageType language,
+ ClangASTMetadata *metadata) {
+ ASTContext *ast = getASTContext();
+ assert(ast != nullptr);
- if (access_type != eAccessNone)
- decl->setAccess (ConvertAccessTypeToAccessSpecifier (access_type));
-
- if (decl_ctx)
- decl_ctx->addDecl (decl);
+ if (decl_ctx == nullptr)
+ decl_ctx = ast->getTranslationUnitDecl();
- return CompilerType(ast, ast->getTagDeclType(decl));
- }
- return CompilerType();
-}
+ if (language == eLanguageTypeObjC ||
+ language == eLanguageTypeObjC_plus_plus) {
+ bool isForwardDecl = true;
+ bool isInternal = false;
+ return CreateObjCClass(name, decl_ctx, isForwardDecl, isInternal, metadata);
+ }
-static TemplateParameterList *
-CreateTemplateParameterList (ASTContext *ast,
- const ClangASTContext::TemplateParameterInfos &template_param_infos,
- llvm::SmallVector<NamedDecl *, 8> &template_param_decls)
-{
- const bool parameter_pack = false;
- const bool is_typename = false;
- const unsigned depth = 0;
- const size_t num_template_params = template_param_infos.GetSize();
- for (size_t i=0; i<num_template_params; ++i)
- {
- const char *name = template_param_infos.names[i];
-
- IdentifierInfo *identifier_info = nullptr;
- if (name && name[0])
- identifier_info = &ast->Idents.get(name);
- if (template_param_infos.args[i].getKind() == TemplateArgument::Integral)
- {
- template_param_decls.push_back (NonTypeTemplateParmDecl::Create (*ast,
- ast->getTranslationUnitDecl(), // Is this the right decl context?, SourceLocation StartLoc,
- SourceLocation(),
- SourceLocation(),
- depth,
- i,
- identifier_info,
- template_param_infos.args[i].getIntegralType(),
- parameter_pack,
- nullptr));
-
- }
- else
- {
- template_param_decls.push_back (TemplateTypeParmDecl::Create (*ast,
- ast->getTranslationUnitDecl(), // Is this the right decl context?
- SourceLocation(),
- SourceLocation(),
- depth,
- i,
- identifier_info,
- is_typename,
- parameter_pack));
- }
- }
+ // NOTE: Eventually CXXRecordDecl will be merged back into RecordDecl and
+ // we will need to update this code. I was told to currently always use
+ // the CXXRecordDecl class since we often don't know from debug information
+ // if something is struct or a class, so we default to always use the more
+ // complete definition just in case.
+
+ bool is_anonymous = (!name) || (!name[0]);
+
+ CXXRecordDecl *decl = CXXRecordDecl::Create(
+ *ast, (TagDecl::TagKind)kind, decl_ctx, SourceLocation(),
+ SourceLocation(), is_anonymous ? nullptr : &ast->Idents.get(name));
+
+ if (is_anonymous)
+ decl->setAnonymousStructOrUnion(true);
- clang::Expr *const requires_clause = nullptr; // TODO: Concepts
- TemplateParameterList *template_param_list = TemplateParameterList::Create (*ast,
- SourceLocation(),
- SourceLocation(),
- template_param_decls,
- SourceLocation(),
- requires_clause);
- return template_param_list;
+ if (decl) {
+ if (metadata)
+ SetMetadata(ast, decl, *metadata);
+
+ if (access_type != eAccessNone)
+ decl->setAccess(ConvertAccessTypeToAccessSpecifier(access_type));
+
+ if (decl_ctx)
+ decl_ctx->addDecl(decl);
+
+ return CompilerType(ast, ast->getTagDeclType(decl));
+ }
+ return CompilerType();
}
-clang::FunctionTemplateDecl *
-ClangASTContext::CreateFunctionTemplateDecl (clang::DeclContext *decl_ctx,
- clang::FunctionDecl *func_decl,
- const char *name,
- const TemplateParameterInfos &template_param_infos)
-{
-// /// \brief Create a function template node.
- ASTContext *ast = getASTContext();
-
- llvm::SmallVector<NamedDecl *, 8> template_param_decls;
-
- TemplateParameterList *template_param_list = CreateTemplateParameterList (ast,
- template_param_infos,
- template_param_decls);
- FunctionTemplateDecl *func_tmpl_decl = FunctionTemplateDecl::Create (*ast,
- decl_ctx,
- func_decl->getLocation(),
- func_decl->getDeclName(),
- template_param_list,
- func_decl);
-
- for (size_t i=0, template_param_decl_count = template_param_decls.size();
- i < template_param_decl_count;
- ++i)
- {
- // TODO: verify which decl context we should put template_param_decls into..
- template_param_decls[i]->setDeclContext (func_decl);
- }
-
- return func_tmpl_decl;
-}
-
-void
-ClangASTContext::CreateFunctionTemplateSpecializationInfo (FunctionDecl *func_decl,
- clang::FunctionTemplateDecl *func_tmpl_decl,
- const TemplateParameterInfos &infos)
-{
- TemplateArgumentList template_args (TemplateArgumentList::OnStack, infos.args);
-
- func_decl->setFunctionTemplateSpecialization (func_tmpl_decl,
- &template_args,
- nullptr);
-}
-
-
-ClassTemplateDecl *
-ClangASTContext::CreateClassTemplateDecl (DeclContext *decl_ctx,
- lldb::AccessType access_type,
- const char *class_name,
- int kind,
- const TemplateParameterInfos &template_param_infos)
-{
- ASTContext *ast = getASTContext();
-
- ClassTemplateDecl *class_template_decl = nullptr;
- if (decl_ctx == nullptr)
- decl_ctx = ast->getTranslationUnitDecl();
-
- IdentifierInfo &identifier_info = ast->Idents.get(class_name);
- DeclarationName decl_name (&identifier_info);
+static TemplateParameterList *CreateTemplateParameterList(
+ ASTContext *ast,
+ const ClangASTContext::TemplateParameterInfos &template_param_infos,
+ llvm::SmallVector<NamedDecl *, 8> &template_param_decls) {
+ const bool parameter_pack = false;
+ const bool is_typename = false;
+ const unsigned depth = 0;
+ const size_t num_template_params = template_param_infos.GetSize();
+ for (size_t i = 0; i < num_template_params; ++i) {
+ const char *name = template_param_infos.names[i];
+
+ IdentifierInfo *identifier_info = nullptr;
+ if (name && name[0])
+ identifier_info = &ast->Idents.get(name);
+ if (template_param_infos.args[i].getKind() == TemplateArgument::Integral) {
+ template_param_decls.push_back(NonTypeTemplateParmDecl::Create(
+ *ast,
+ ast->getTranslationUnitDecl(), // Is this the right decl context?,
+ // SourceLocation StartLoc,
+ SourceLocation(), SourceLocation(), depth, i, identifier_info,
+ template_param_infos.args[i].getIntegralType(), parameter_pack,
+ nullptr));
+
+ } else {
+ template_param_decls.push_back(TemplateTypeParmDecl::Create(
+ *ast,
+ ast->getTranslationUnitDecl(), // Is this the right decl context?
+ SourceLocation(), SourceLocation(), depth, i, identifier_info,
+ is_typename, parameter_pack));
+ }
+ }
+
+ clang::Expr *const requires_clause = nullptr; // TODO: Concepts
+ TemplateParameterList *template_param_list = TemplateParameterList::Create(
+ *ast, SourceLocation(), SourceLocation(), template_param_decls,
+ SourceLocation(), requires_clause);
+ return template_param_list;
+}
+
+clang::FunctionTemplateDecl *ClangASTContext::CreateFunctionTemplateDecl(
+ clang::DeclContext *decl_ctx, clang::FunctionDecl *func_decl,
+ const char *name, const TemplateParameterInfos &template_param_infos) {
+ // /// \brief Create a function template node.
+ ASTContext *ast = getASTContext();
+
+ llvm::SmallVector<NamedDecl *, 8> template_param_decls;
+
+ TemplateParameterList *template_param_list = CreateTemplateParameterList(
+ ast, template_param_infos, template_param_decls);
+ FunctionTemplateDecl *func_tmpl_decl = FunctionTemplateDecl::Create(
+ *ast, decl_ctx, func_decl->getLocation(), func_decl->getDeclName(),
+ template_param_list, func_decl);
+
+ for (size_t i = 0, template_param_decl_count = template_param_decls.size();
+ i < template_param_decl_count; ++i) {
+ // TODO: verify which decl context we should put template_param_decls into..
+ template_param_decls[i]->setDeclContext(func_decl);
+ }
+
+ return func_tmpl_decl;
+}
+
+void ClangASTContext::CreateFunctionTemplateSpecializationInfo(
+ FunctionDecl *func_decl, clang::FunctionTemplateDecl *func_tmpl_decl,
+ const TemplateParameterInfos &infos) {
+ TemplateArgumentList template_args(TemplateArgumentList::OnStack, infos.args);
+
+ func_decl->setFunctionTemplateSpecialization(func_tmpl_decl, &template_args,
+ nullptr);
+}
- clang::DeclContext::lookup_result result = decl_ctx->lookup(decl_name);
-
- for (NamedDecl *decl : result)
- {
- class_template_decl = dyn_cast<clang::ClassTemplateDecl>(decl);
- if (class_template_decl)
- return class_template_decl;
- }
-
- llvm::SmallVector<NamedDecl *, 8> template_param_decls;
-
- TemplateParameterList *template_param_list = CreateTemplateParameterList (ast,
- template_param_infos,
- template_param_decls);
-
- CXXRecordDecl *template_cxx_decl = CXXRecordDecl::Create (*ast,
- (TagDecl::TagKind)kind,
- decl_ctx, // What decl context do we use here? TU? The actual decl context?
- SourceLocation(),
- SourceLocation(),
- &identifier_info);
-
- for (size_t i=0, template_param_decl_count = template_param_decls.size();
- i < template_param_decl_count;
- ++i)
- {
- template_param_decls[i]->setDeclContext (template_cxx_decl);
- }
-
- // With templated classes, we say that a class is templated with
- // specializations, but that the bare class has no functions.
- //template_cxx_decl->startDefinition();
- //template_cxx_decl->completeDefinition();
-
- class_template_decl = ClassTemplateDecl::Create (*ast,
- decl_ctx, // What decl context do we use here? TU? The actual decl context?
- SourceLocation(),
- decl_name,
- template_param_list,
- template_cxx_decl,
- nullptr);
-
+ClassTemplateDecl *ClangASTContext::CreateClassTemplateDecl(
+ DeclContext *decl_ctx, lldb::AccessType access_type, const char *class_name,
+ int kind, const TemplateParameterInfos &template_param_infos) {
+ ASTContext *ast = getASTContext();
+
+ ClassTemplateDecl *class_template_decl = nullptr;
+ if (decl_ctx == nullptr)
+ decl_ctx = ast->getTranslationUnitDecl();
+
+ IdentifierInfo &identifier_info = ast->Idents.get(class_name);
+ DeclarationName decl_name(&identifier_info);
+
+ clang::DeclContext::lookup_result result = decl_ctx->lookup(decl_name);
+
+ for (NamedDecl *decl : result) {
+ class_template_decl = dyn_cast<clang::ClassTemplateDecl>(decl);
if (class_template_decl)
- {
- if (access_type != eAccessNone)
- class_template_decl->setAccess (ConvertAccessTypeToAccessSpecifier (access_type));
-
- //if (TagDecl *ctx_tag_decl = dyn_cast<TagDecl>(decl_ctx))
- // CompleteTagDeclarationDefinition(GetTypeForDecl(ctx_tag_decl));
-
- decl_ctx->addDecl (class_template_decl);
-
+ return class_template_decl;
+ }
+
+ llvm::SmallVector<NamedDecl *, 8> template_param_decls;
+
+ TemplateParameterList *template_param_list = CreateTemplateParameterList(
+ ast, template_param_infos, template_param_decls);
+
+ CXXRecordDecl *template_cxx_decl = CXXRecordDecl::Create(
+ *ast, (TagDecl::TagKind)kind,
+ decl_ctx, // What decl context do we use here? TU? The actual decl
+ // context?
+ SourceLocation(), SourceLocation(), &identifier_info);
+
+ for (size_t i = 0, template_param_decl_count = template_param_decls.size();
+ i < template_param_decl_count; ++i) {
+ template_param_decls[i]->setDeclContext(template_cxx_decl);
+ }
+
+ // With templated classes, we say that a class is templated with
+ // specializations, but that the bare class has no functions.
+ // template_cxx_decl->startDefinition();
+ // template_cxx_decl->completeDefinition();
+
+ class_template_decl = ClassTemplateDecl::Create(
+ *ast,
+ decl_ctx, // What decl context do we use here? TU? The actual decl
+ // context?
+ SourceLocation(), decl_name, template_param_list, template_cxx_decl,
+ nullptr);
+
+ if (class_template_decl) {
+ if (access_type != eAccessNone)
+ class_template_decl->setAccess(
+ ConvertAccessTypeToAccessSpecifier(access_type));
+
+ // if (TagDecl *ctx_tag_decl = dyn_cast<TagDecl>(decl_ctx))
+ // CompleteTagDeclarationDefinition(GetTypeForDecl(ctx_tag_decl));
+
+ decl_ctx->addDecl(class_template_decl);
+
#ifdef LLDB_CONFIGURATION_DEBUG
- VerifyDecl(class_template_decl);
+ VerifyDecl(class_template_decl);
#endif
- }
+ }
- return class_template_decl;
+ return class_template_decl;
}
-
ClassTemplateSpecializationDecl *
-ClangASTContext::CreateClassTemplateSpecializationDecl (DeclContext *decl_ctx,
- ClassTemplateDecl *class_template_decl,
- int kind,
- const TemplateParameterInfos &template_param_infos)
-{
- ASTContext *ast = getASTContext();
- ClassTemplateSpecializationDecl *class_template_specialization_decl = ClassTemplateSpecializationDecl::Create (*ast,
- (TagDecl::TagKind)kind,
- decl_ctx,
- SourceLocation(),
- SourceLocation(),
- class_template_decl,
- template_param_infos.args,
- nullptr);
-
- class_template_specialization_decl->setSpecializationKind(TSK_ExplicitSpecialization);
-
- return class_template_specialization_decl;
-}
+ClangASTContext::CreateClassTemplateSpecializationDecl(
+ DeclContext *decl_ctx, ClassTemplateDecl *class_template_decl, int kind,
+ const TemplateParameterInfos &template_param_infos) {
+ ASTContext *ast = getASTContext();
+ ClassTemplateSpecializationDecl *class_template_specialization_decl =
+ ClassTemplateSpecializationDecl::Create(
+ *ast, (TagDecl::TagKind)kind, decl_ctx, SourceLocation(),
+ SourceLocation(), class_template_decl, template_param_infos.args,
+ nullptr);
-CompilerType
-ClangASTContext::CreateClassTemplateSpecializationType (ClassTemplateSpecializationDecl *class_template_specialization_decl)
-{
- if (class_template_specialization_decl)
- {
- ASTContext *ast = getASTContext();
- if (ast)
- return CompilerType(ast, ast->getTagDeclType(class_template_specialization_decl));
- }
- return CompilerType();
+ class_template_specialization_decl->setSpecializationKind(
+ TSK_ExplicitSpecialization);
+
+ return class_template_specialization_decl;
}
-static inline bool
-check_op_param(bool is_method, clang::OverloadedOperatorKind op_kind, bool unary, bool binary, uint32_t num_params)
-{
- // Special-case call since it can take any number of operands
- if(op_kind == OO_Call)
- return true;
-
- // The parameter count doesn't include "this"
- if (is_method)
- ++num_params;
- if (num_params == 1)
- return unary;
- if (num_params == 2)
- return binary;
- else
+CompilerType ClangASTContext::CreateClassTemplateSpecializationType(
+ ClassTemplateSpecializationDecl *class_template_specialization_decl) {
+ if (class_template_specialization_decl) {
+ ASTContext *ast = getASTContext();
+ if (ast)
+ return CompilerType(
+ ast, ast->getTagDeclType(class_template_specialization_decl));
+ }
+ return CompilerType();
+}
+
+static inline bool check_op_param(bool is_method,
+ clang::OverloadedOperatorKind op_kind,
+ bool unary, bool binary,
+ uint32_t num_params) {
+ // Special-case call since it can take any number of operands
+ if (op_kind == OO_Call)
+ return true;
+
+ // The parameter count doesn't include "this"
+ if (is_method)
+ ++num_params;
+ if (num_params == 1)
+ return unary;
+ if (num_params == 2)
+ return binary;
+ else
return false;
}
-bool
-ClangASTContext::CheckOverloadedOperatorKindParameterCount(bool is_method, clang::OverloadedOperatorKind op_kind,
- uint32_t num_params)
-{
- switch (op_kind)
- {
- default:
- break;
- // C++ standard allows any number of arguments to new/delete
- case OO_New:
- case OO_Array_New:
- case OO_Delete:
- case OO_Array_Delete:
- return true;
- }
+bool ClangASTContext::CheckOverloadedOperatorKindParameterCount(
+ bool is_method, clang::OverloadedOperatorKind op_kind,
+ uint32_t num_params) {
+ switch (op_kind) {
+ default:
+ break;
+ // C++ standard allows any number of arguments to new/delete
+ case OO_New:
+ case OO_Array_New:
+ case OO_Delete:
+ case OO_Array_Delete:
+ return true;
+ }
-#define OVERLOADED_OPERATOR(Name, Spelling, Token, Unary, Binary, MemberOnly) \
- case OO_##Name: \
- return check_op_param(is_method, op_kind, Unary, Binary, num_params);
- switch (op_kind)
- {
+#define OVERLOADED_OPERATOR(Name, Spelling, Token, Unary, Binary, MemberOnly) \
+ case OO_##Name: \
+ return check_op_param(is_method, op_kind, Unary, Binary, num_params);
+ switch (op_kind) {
#include "clang/Basic/OperatorKinds.def"
- default: break;
- }
- return false;
+ default:
+ break;
+ }
+ return false;
}
clang::AccessSpecifier
-ClangASTContext::UnifyAccessSpecifiers (clang::AccessSpecifier lhs, clang::AccessSpecifier rhs)
-{
- // Make the access equal to the stricter of the field and the nested field's access
- if (lhs == AS_none || rhs == AS_none)
- return AS_none;
- if (lhs == AS_private || rhs == AS_private)
- return AS_private;
- if (lhs == AS_protected || rhs == AS_protected)
- return AS_protected;
- return AS_public;
+ClangASTContext::UnifyAccessSpecifiers(clang::AccessSpecifier lhs,
+ clang::AccessSpecifier rhs) {
+ // Make the access equal to the stricter of the field and the nested field's
+ // access
+ if (lhs == AS_none || rhs == AS_none)
+ return AS_none;
+ if (lhs == AS_private || rhs == AS_private)
+ return AS_private;
+ if (lhs == AS_protected || rhs == AS_protected)
+ return AS_protected;
+ return AS_public;
}
-bool
-ClangASTContext::FieldIsBitfield (FieldDecl* field, uint32_t& bitfield_bit_size)
-{
- return FieldIsBitfield(getASTContext(), field, bitfield_bit_size);
+bool ClangASTContext::FieldIsBitfield(FieldDecl *field,
+ uint32_t &bitfield_bit_size) {
+ return FieldIsBitfield(getASTContext(), field, bitfield_bit_size);
}
-bool
-ClangASTContext::FieldIsBitfield
-(
- ASTContext *ast,
- FieldDecl* field,
- uint32_t& bitfield_bit_size
-)
-{
- if (ast == nullptr || field == nullptr)
- return false;
+bool ClangASTContext::FieldIsBitfield(ASTContext *ast, FieldDecl *field,
+ uint32_t &bitfield_bit_size) {
+ if (ast == nullptr || field == nullptr)
+ return false;
- if (field->isBitField())
- {
- Expr* bit_width_expr = field->getBitWidth();
- if (bit_width_expr)
- {
- llvm::APSInt bit_width_apsint;
- if (bit_width_expr->isIntegerConstantExpr(bit_width_apsint, *ast))
- {
- bitfield_bit_size = bit_width_apsint.getLimitedValue(UINT32_MAX);
- return true;
- }
- }
+ if (field->isBitField()) {
+ Expr *bit_width_expr = field->getBitWidth();
+ if (bit_width_expr) {
+ llvm::APSInt bit_width_apsint;
+ if (bit_width_expr->isIntegerConstantExpr(bit_width_apsint, *ast)) {
+ bitfield_bit_size = bit_width_apsint.getLimitedValue(UINT32_MAX);
+ return true;
+ }
}
- return false;
+ }
+ return false;
}
-bool
-ClangASTContext::RecordHasFields (const RecordDecl *record_decl)
-{
- if (record_decl == nullptr)
- return false;
+bool ClangASTContext::RecordHasFields(const RecordDecl *record_decl) {
+ if (record_decl == nullptr)
+ return false;
- if (!record_decl->field_empty())
- return true;
+ if (!record_decl->field_empty())
+ return true;
- // No fields, lets check this is a CXX record and check the base classes
- const CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_decl);
- if (cxx_record_decl)
- {
- CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
- for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end();
- base_class != base_class_end;
- ++base_class)
- {
- const CXXRecordDecl *base_class_decl = cast<CXXRecordDecl>(base_class->getType()->getAs<RecordType>()->getDecl());
- if (RecordHasFields(base_class_decl))
- return true;
- }
+ // No fields, lets check this is a CXX record and check the base classes
+ const CXXRecordDecl *cxx_record_decl = dyn_cast<CXXRecordDecl>(record_decl);
+ if (cxx_record_decl) {
+ CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
+ for (base_class = cxx_record_decl->bases_begin(),
+ base_class_end = cxx_record_decl->bases_end();
+ base_class != base_class_end; ++base_class) {
+ const CXXRecordDecl *base_class_decl = cast<CXXRecordDecl>(
+ base_class->getType()->getAs<RecordType>()->getDecl());
+ if (RecordHasFields(base_class_decl))
+ return true;
}
- return false;
+ }
+ return false;
}
#pragma mark Objective C Classes
-CompilerType
-ClangASTContext::CreateObjCClass
-(
- const char *name,
- DeclContext *decl_ctx,
- bool isForwardDecl,
- bool isInternal,
- ClangASTMetadata *metadata
-)
-{
- ASTContext *ast = getASTContext();
- assert (ast != nullptr);
- assert (name && name[0]);
- if (decl_ctx == nullptr)
- decl_ctx = ast->getTranslationUnitDecl();
-
- ObjCInterfaceDecl *decl = ObjCInterfaceDecl::Create (*ast,
- decl_ctx,
- SourceLocation(),
- &ast->Idents.get(name),
- nullptr,
- nullptr,
- SourceLocation(),
- /*isForwardDecl,*/
- isInternal);
-
- if (decl && metadata)
- SetMetadata(ast, decl, *metadata);
-
- return CompilerType (ast, ast->getObjCInterfaceType(decl));
+CompilerType ClangASTContext::CreateObjCClass(const char *name,
+ DeclContext *decl_ctx,
+ bool isForwardDecl,
+ bool isInternal,
+ ClangASTMetadata *metadata) {
+ ASTContext *ast = getASTContext();
+ assert(ast != nullptr);
+ assert(name && name[0]);
+ if (decl_ctx == nullptr)
+ decl_ctx = ast->getTranslationUnitDecl();
+
+ ObjCInterfaceDecl *decl = ObjCInterfaceDecl::Create(
+ *ast, decl_ctx, SourceLocation(), &ast->Idents.get(name), nullptr,
+ nullptr, SourceLocation(),
+ /*isForwardDecl,*/
+ isInternal);
+
+ if (decl && metadata)
+ SetMetadata(ast, decl, *metadata);
+
+ return CompilerType(ast, ast->getObjCInterfaceType(decl));
}
-static inline bool
-BaseSpecifierIsEmpty (const CXXBaseSpecifier *b)
-{
- return ClangASTContext::RecordHasFields(b->getType()->getAsCXXRecordDecl()) == false;
+static inline bool BaseSpecifierIsEmpty(const CXXBaseSpecifier *b) {
+ return ClangASTContext::RecordHasFields(b->getType()->getAsCXXRecordDecl()) ==
+ false;
}
uint32_t
-ClangASTContext::GetNumBaseClasses (const CXXRecordDecl *cxx_record_decl, bool omit_empty_base_classes)
-{
- uint32_t num_bases = 0;
- if (cxx_record_decl)
- {
- if (omit_empty_base_classes)
- {
- CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
- for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end();
- base_class != base_class_end;
- ++base_class)
- {
- // Skip empty base classes
- if (omit_empty_base_classes)
- {
- if (BaseSpecifierIsEmpty (base_class))
- continue;
- }
- ++num_bases;
- }
+ClangASTContext::GetNumBaseClasses(const CXXRecordDecl *cxx_record_decl,
+ bool omit_empty_base_classes) {
+ uint32_t num_bases = 0;
+ if (cxx_record_decl) {
+ if (omit_empty_base_classes) {
+ CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
+ for (base_class = cxx_record_decl->bases_begin(),
+ base_class_end = cxx_record_decl->bases_end();
+ base_class != base_class_end; ++base_class) {
+ // Skip empty base classes
+ if (omit_empty_base_classes) {
+ if (BaseSpecifierIsEmpty(base_class))
+ continue;
}
- else
- num_bases = cxx_record_decl->getNumBases();
- }
- return num_bases;
+ ++num_bases;
+ }
+ } else
+ num_bases = cxx_record_decl->getNumBases();
+ }
+ return num_bases;
}
-
#pragma mark Namespace Declarations
NamespaceDecl *
-ClangASTContext::GetUniqueNamespaceDeclaration (const char *name, DeclContext *decl_ctx)
-{
- NamespaceDecl *namespace_decl = nullptr;
- ASTContext *ast = getASTContext();
- TranslationUnitDecl *translation_unit_decl = ast->getTranslationUnitDecl ();
- if (decl_ctx == nullptr)
- decl_ctx = translation_unit_decl;
-
- if (name)
- {
- IdentifierInfo &identifier_info = ast->Idents.get(name);
- DeclarationName decl_name (&identifier_info);
- clang::DeclContext::lookup_result result = decl_ctx->lookup(decl_name);
- for (NamedDecl *decl : result)
- {
- namespace_decl = dyn_cast<clang::NamespaceDecl>(decl);
- if (namespace_decl)
- return namespace_decl;
- }
-
- namespace_decl = NamespaceDecl::Create(*ast,
- decl_ctx,
- false,
- SourceLocation(),
- SourceLocation(),
- &identifier_info,
- nullptr);
-
- decl_ctx->addDecl (namespace_decl);
- }
- else
- {
- if (decl_ctx == translation_unit_decl)
- {
- namespace_decl = translation_unit_decl->getAnonymousNamespace();
- if (namespace_decl)
- return namespace_decl;
-
- namespace_decl = NamespaceDecl::Create(*ast,
- decl_ctx,
- false,
- SourceLocation(),
- SourceLocation(),
- nullptr,
- nullptr);
- translation_unit_decl->setAnonymousNamespace (namespace_decl);
- translation_unit_decl->addDecl (namespace_decl);
- assert (namespace_decl == translation_unit_decl->getAnonymousNamespace());
- }
- else
- {
- NamespaceDecl *parent_namespace_decl = cast<NamespaceDecl>(decl_ctx);
- if (parent_namespace_decl)
- {
- namespace_decl = parent_namespace_decl->getAnonymousNamespace();
- if (namespace_decl)
- return namespace_decl;
- namespace_decl = NamespaceDecl::Create(*ast,
- decl_ctx,
- false,
- SourceLocation(),
- SourceLocation(),
- nullptr,
- nullptr);
- parent_namespace_decl->setAnonymousNamespace (namespace_decl);
- parent_namespace_decl->addDecl (namespace_decl);
- assert (namespace_decl == parent_namespace_decl->getAnonymousNamespace());
- }
- else
- {
- // BAD!!!
- }
- }
- }
+ClangASTContext::GetUniqueNamespaceDeclaration(const char *name,
+ DeclContext *decl_ctx) {
+ NamespaceDecl *namespace_decl = nullptr;
+ ASTContext *ast = getASTContext();
+ TranslationUnitDecl *translation_unit_decl = ast->getTranslationUnitDecl();
+ if (decl_ctx == nullptr)
+ decl_ctx = translation_unit_decl;
+
+ if (name) {
+ IdentifierInfo &identifier_info = ast->Idents.get(name);
+ DeclarationName decl_name(&identifier_info);
+ clang::DeclContext::lookup_result result = decl_ctx->lookup(decl_name);
+ for (NamedDecl *decl : result) {
+ namespace_decl = dyn_cast<clang::NamespaceDecl>(decl);
+ if (namespace_decl)
+ return namespace_decl;
+ }
+
+ namespace_decl =
+ NamespaceDecl::Create(*ast, decl_ctx, false, SourceLocation(),
+ SourceLocation(), &identifier_info, nullptr);
+
+ decl_ctx->addDecl(namespace_decl);
+ } else {
+ if (decl_ctx == translation_unit_decl) {
+ namespace_decl = translation_unit_decl->getAnonymousNamespace();
+ if (namespace_decl)
+ return namespace_decl;
+
+ namespace_decl =
+ NamespaceDecl::Create(*ast, decl_ctx, false, SourceLocation(),
+ SourceLocation(), nullptr, nullptr);
+ translation_unit_decl->setAnonymousNamespace(namespace_decl);
+ translation_unit_decl->addDecl(namespace_decl);
+ assert(namespace_decl == translation_unit_decl->getAnonymousNamespace());
+ } else {
+ NamespaceDecl *parent_namespace_decl = cast<NamespaceDecl>(decl_ctx);
+ if (parent_namespace_decl) {
+ namespace_decl = parent_namespace_decl->getAnonymousNamespace();
+ if (namespace_decl)
+ return namespace_decl;
+ namespace_decl =
+ NamespaceDecl::Create(*ast, decl_ctx, false, SourceLocation(),
+ SourceLocation(), nullptr, nullptr);
+ parent_namespace_decl->setAnonymousNamespace(namespace_decl);
+ parent_namespace_decl->addDecl(namespace_decl);
+ assert(namespace_decl ==
+ parent_namespace_decl->getAnonymousNamespace());
+ } else {
+ // BAD!!!
+ }
+ }
+ }
#ifdef LLDB_CONFIGURATION_DEBUG
- VerifyDecl(namespace_decl);
+ VerifyDecl(namespace_decl);
#endif
- return namespace_decl;
+ return namespace_decl;
}
-NamespaceDecl *
-ClangASTContext::GetUniqueNamespaceDeclaration (clang::ASTContext *ast,
- const char *name,
- clang::DeclContext *decl_ctx)
-{
- ClangASTContext *ast_ctx = ClangASTContext::GetASTContext(ast);
- if (ast_ctx == nullptr)
- return nullptr;
+NamespaceDecl *ClangASTContext::GetUniqueNamespaceDeclaration(
+ clang::ASTContext *ast, const char *name, clang::DeclContext *decl_ctx) {
+ ClangASTContext *ast_ctx = ClangASTContext::GetASTContext(ast);
+ if (ast_ctx == nullptr)
+ return nullptr;
- return ast_ctx->GetUniqueNamespaceDeclaration(name, decl_ctx);
+ return ast_ctx->GetUniqueNamespaceDeclaration(name, decl_ctx);
}
clang::BlockDecl *
-ClangASTContext::CreateBlockDeclaration (clang::DeclContext *ctx)
-{
- if (ctx != nullptr)
- {
- clang::BlockDecl *decl = clang::BlockDecl::Create(*getASTContext(), ctx, clang::SourceLocation());
- ctx->addDecl(decl);
- return decl;
- }
+ClangASTContext::CreateBlockDeclaration(clang::DeclContext *ctx) {
+ if (ctx != nullptr) {
+ clang::BlockDecl *decl = clang::BlockDecl::Create(*getASTContext(), ctx,
+ clang::SourceLocation());
+ ctx->addDecl(decl);
+ return decl;
+ }
+ return nullptr;
+}
+
+clang::DeclContext *FindLCABetweenDecls(clang::DeclContext *left,
+ clang::DeclContext *right,
+ clang::DeclContext *root) {
+ if (root == nullptr)
return nullptr;
-}
-
-clang::DeclContext *
-FindLCABetweenDecls(clang::DeclContext *left, clang::DeclContext *right, clang::DeclContext *root)
-{
- if (root == nullptr)
- return nullptr;
- std::set<clang::DeclContext *> path_left;
- for (clang::DeclContext *d = left; d != nullptr; d = d->getParent())
- path_left.insert(d);
+ std::set<clang::DeclContext *> path_left;
+ for (clang::DeclContext *d = left; d != nullptr; d = d->getParent())
+ path_left.insert(d);
- for (clang::DeclContext *d = right; d != nullptr; d = d->getParent())
- if (path_left.find(d) != path_left.end())
- return d;
+ for (clang::DeclContext *d = right; d != nullptr; d = d->getParent())
+ if (path_left.find(d) != path_left.end())
+ return d;
- return nullptr;
+ return nullptr;
}
-clang::UsingDirectiveDecl *
-ClangASTContext::CreateUsingDirectiveDeclaration (clang::DeclContext *decl_ctx, clang::NamespaceDecl *ns_decl)
-{
- if (decl_ctx != nullptr && ns_decl != nullptr)
- {
- clang::TranslationUnitDecl *translation_unit = (clang::TranslationUnitDecl *)GetTranslationUnitDecl(getASTContext());
- clang::UsingDirectiveDecl *using_decl = clang::UsingDirectiveDecl::Create(*getASTContext(),
- decl_ctx,
- clang::SourceLocation(),
- clang::SourceLocation(),
- clang::NestedNameSpecifierLoc(),
- clang::SourceLocation(),
- ns_decl,
- FindLCABetweenDecls(decl_ctx, ns_decl, translation_unit));
- decl_ctx->addDecl(using_decl);
- return using_decl;
- }
- return nullptr;
+clang::UsingDirectiveDecl *ClangASTContext::CreateUsingDirectiveDeclaration(
+ clang::DeclContext *decl_ctx, clang::NamespaceDecl *ns_decl) {
+ if (decl_ctx != nullptr && ns_decl != nullptr) {
+ clang::TranslationUnitDecl *translation_unit =
+ (clang::TranslationUnitDecl *)GetTranslationUnitDecl(getASTContext());
+ clang::UsingDirectiveDecl *using_decl = clang::UsingDirectiveDecl::Create(
+ *getASTContext(), decl_ctx, clang::SourceLocation(),
+ clang::SourceLocation(), clang::NestedNameSpecifierLoc(),
+ clang::SourceLocation(), ns_decl,
+ FindLCABetweenDecls(decl_ctx, ns_decl, translation_unit));
+ decl_ctx->addDecl(using_decl);
+ return using_decl;
+ }
+ return nullptr;
}
clang::UsingDecl *
-ClangASTContext::CreateUsingDeclaration (clang::DeclContext *current_decl_ctx, clang::NamedDecl *target)
-{
- if (current_decl_ctx != nullptr && target != nullptr)
- {
- clang::UsingDecl *using_decl = clang::UsingDecl::Create(*getASTContext(),
- current_decl_ctx,
- clang::SourceLocation(),
- clang::NestedNameSpecifierLoc(),
- clang::DeclarationNameInfo(),
- false);
- clang::UsingShadowDecl *shadow_decl = clang::UsingShadowDecl::Create(*getASTContext(),
- current_decl_ctx,
- clang::SourceLocation(),
- using_decl,
- target);
- using_decl->addShadowDecl(shadow_decl);
- current_decl_ctx->addDecl(using_decl);
- return using_decl;
- }
- return nullptr;
-}
-
-clang::VarDecl *
-ClangASTContext::CreateVariableDeclaration (clang::DeclContext *decl_context, const char *name, clang::QualType type)
-{
- if (decl_context != nullptr)
- {
- clang::VarDecl *var_decl = clang::VarDecl::Create(*getASTContext(),
- decl_context,
- clang::SourceLocation(),
- clang::SourceLocation(),
- name && name[0] ? &getASTContext()->Idents.getOwn(name) : nullptr,
- type,
- nullptr,
- clang::SC_None);
- var_decl->setAccess(clang::AS_public);
- decl_context->addDecl(var_decl);
- return var_decl;
- }
- return nullptr;
+ClangASTContext::CreateUsingDeclaration(clang::DeclContext *current_decl_ctx,
+ clang::NamedDecl *target) {
+ if (current_decl_ctx != nullptr && target != nullptr) {
+ clang::UsingDecl *using_decl = clang::UsingDecl::Create(
+ *getASTContext(), current_decl_ctx, clang::SourceLocation(),
+ clang::NestedNameSpecifierLoc(), clang::DeclarationNameInfo(), false);
+ clang::UsingShadowDecl *shadow_decl = clang::UsingShadowDecl::Create(
+ *getASTContext(), current_decl_ctx, clang::SourceLocation(), using_decl,
+ target);
+ using_decl->addShadowDecl(shadow_decl);
+ current_decl_ctx->addDecl(using_decl);
+ return using_decl;
+ }
+ return nullptr;
+}
+
+clang::VarDecl *ClangASTContext::CreateVariableDeclaration(
+ clang::DeclContext *decl_context, const char *name, clang::QualType type) {
+ if (decl_context != nullptr) {
+ clang::VarDecl *var_decl = clang::VarDecl::Create(
+ *getASTContext(), decl_context, clang::SourceLocation(),
+ clang::SourceLocation(),
+ name && name[0] ? &getASTContext()->Idents.getOwn(name) : nullptr, type,
+ nullptr, clang::SC_None);
+ var_decl->setAccess(clang::AS_public);
+ decl_context->addDecl(var_decl);
+ return var_decl;
+ }
+ return nullptr;
}
lldb::opaque_compiler_type_t
-ClangASTContext::GetOpaqueCompilerType(clang::ASTContext *ast, lldb::BasicType basic_type)
-{
- switch (basic_type)
- {
- case eBasicTypeVoid:
- return ast->VoidTy.getAsOpaquePtr();
- case eBasicTypeChar:
- return ast->CharTy.getAsOpaquePtr();
- case eBasicTypeSignedChar:
- return ast->SignedCharTy.getAsOpaquePtr();
- case eBasicTypeUnsignedChar:
- return ast->UnsignedCharTy.getAsOpaquePtr();
- case eBasicTypeWChar:
- return ast->getWCharType().getAsOpaquePtr();
- case eBasicTypeSignedWChar:
- return ast->getSignedWCharType().getAsOpaquePtr();
- case eBasicTypeUnsignedWChar:
- return ast->getUnsignedWCharType().getAsOpaquePtr();
- case eBasicTypeChar16:
- return ast->Char16Ty.getAsOpaquePtr();
- case eBasicTypeChar32:
- return ast->Char32Ty.getAsOpaquePtr();
- case eBasicTypeShort:
- return ast->ShortTy.getAsOpaquePtr();
- case eBasicTypeUnsignedShort:
- return ast->UnsignedShortTy.getAsOpaquePtr();
- case eBasicTypeInt:
- return ast->IntTy.getAsOpaquePtr();
- case eBasicTypeUnsignedInt:
- return ast->UnsignedIntTy.getAsOpaquePtr();
- case eBasicTypeLong:
- return ast->LongTy.getAsOpaquePtr();
- case eBasicTypeUnsignedLong:
- return ast->UnsignedLongTy.getAsOpaquePtr();
- case eBasicTypeLongLong:
- return ast->LongLongTy.getAsOpaquePtr();
- case eBasicTypeUnsignedLongLong:
- return ast->UnsignedLongLongTy.getAsOpaquePtr();
- case eBasicTypeInt128:
- return ast->Int128Ty.getAsOpaquePtr();
- case eBasicTypeUnsignedInt128:
- return ast->UnsignedInt128Ty.getAsOpaquePtr();
- case eBasicTypeBool:
- return ast->BoolTy.getAsOpaquePtr();
- case eBasicTypeHalf:
- return ast->HalfTy.getAsOpaquePtr();
- case eBasicTypeFloat:
- return ast->FloatTy.getAsOpaquePtr();
- case eBasicTypeDouble:
- return ast->DoubleTy.getAsOpaquePtr();
- case eBasicTypeLongDouble:
- return ast->LongDoubleTy.getAsOpaquePtr();
- case eBasicTypeFloatComplex:
- return ast->FloatComplexTy.getAsOpaquePtr();
- case eBasicTypeDoubleComplex:
- return ast->DoubleComplexTy.getAsOpaquePtr();
- case eBasicTypeLongDoubleComplex:
- return ast->LongDoubleComplexTy.getAsOpaquePtr();
- case eBasicTypeObjCID:
- return ast->getObjCIdType().getAsOpaquePtr();
- case eBasicTypeObjCClass:
- return ast->getObjCClassType().getAsOpaquePtr();
- case eBasicTypeObjCSel:
- return ast->getObjCSelType().getAsOpaquePtr();
- case eBasicTypeNullPtr:
- return ast->NullPtrTy.getAsOpaquePtr();
- default:
- return nullptr;
- }
+ClangASTContext::GetOpaqueCompilerType(clang::ASTContext *ast,
+ lldb::BasicType basic_type) {
+ switch (basic_type) {
+ case eBasicTypeVoid:
+ return ast->VoidTy.getAsOpaquePtr();
+ case eBasicTypeChar:
+ return ast->CharTy.getAsOpaquePtr();
+ case eBasicTypeSignedChar:
+ return ast->SignedCharTy.getAsOpaquePtr();
+ case eBasicTypeUnsignedChar:
+ return ast->UnsignedCharTy.getAsOpaquePtr();
+ case eBasicTypeWChar:
+ return ast->getWCharType().getAsOpaquePtr();
+ case eBasicTypeSignedWChar:
+ return ast->getSignedWCharType().getAsOpaquePtr();
+ case eBasicTypeUnsignedWChar:
+ return ast->getUnsignedWCharType().getAsOpaquePtr();
+ case eBasicTypeChar16:
+ return ast->Char16Ty.getAsOpaquePtr();
+ case eBasicTypeChar32:
+ return ast->Char32Ty.getAsOpaquePtr();
+ case eBasicTypeShort:
+ return ast->ShortTy.getAsOpaquePtr();
+ case eBasicTypeUnsignedShort:
+ return ast->UnsignedShortTy.getAsOpaquePtr();
+ case eBasicTypeInt:
+ return ast->IntTy.getAsOpaquePtr();
+ case eBasicTypeUnsignedInt:
+ return ast->UnsignedIntTy.getAsOpaquePtr();
+ case eBasicTypeLong:
+ return ast->LongTy.getAsOpaquePtr();
+ case eBasicTypeUnsignedLong:
+ return ast->UnsignedLongTy.getAsOpaquePtr();
+ case eBasicTypeLongLong:
+ return ast->LongLongTy.getAsOpaquePtr();
+ case eBasicTypeUnsignedLongLong:
+ return ast->UnsignedLongLongTy.getAsOpaquePtr();
+ case eBasicTypeInt128:
+ return ast->Int128Ty.getAsOpaquePtr();
+ case eBasicTypeUnsignedInt128:
+ return ast->UnsignedInt128Ty.getAsOpaquePtr();
+ case eBasicTypeBool:
+ return ast->BoolTy.getAsOpaquePtr();
+ case eBasicTypeHalf:
+ return ast->HalfTy.getAsOpaquePtr();
+ case eBasicTypeFloat:
+ return ast->FloatTy.getAsOpaquePtr();
+ case eBasicTypeDouble:
+ return ast->DoubleTy.getAsOpaquePtr();
+ case eBasicTypeLongDouble:
+ return ast->LongDoubleTy.getAsOpaquePtr();
+ case eBasicTypeFloatComplex:
+ return ast->FloatComplexTy.getAsOpaquePtr();
+ case eBasicTypeDoubleComplex:
+ return ast->DoubleComplexTy.getAsOpaquePtr();
+ case eBasicTypeLongDoubleComplex:
+ return ast->LongDoubleComplexTy.getAsOpaquePtr();
+ case eBasicTypeObjCID:
+ return ast->getObjCIdType().getAsOpaquePtr();
+ case eBasicTypeObjCClass:
+ return ast->getObjCClassType().getAsOpaquePtr();
+ case eBasicTypeObjCSel:
+ return ast->getObjCSelType().getAsOpaquePtr();
+ case eBasicTypeNullPtr:
+ return ast->NullPtrTy.getAsOpaquePtr();
+ default:
+ return nullptr;
+ }
}
#pragma mark Function Types
clang::DeclarationName
-ClangASTContext::GetDeclarationName(const char *name, const CompilerType &function_clang_type)
-{
- if (!name || !name[0])
- return clang::DeclarationName();
+ClangASTContext::GetDeclarationName(const char *name,
+ const CompilerType &function_clang_type) {
+ if (!name || !name[0])
+ return clang::DeclarationName();
+
+ clang::OverloadedOperatorKind op_kind = clang::NUM_OVERLOADED_OPERATORS;
+ if (!IsOperator(name, op_kind) || op_kind == clang::NUM_OVERLOADED_OPERATORS)
+ return DeclarationName(&getASTContext()->Idents.get(
+ name)); // Not operator, but a regular function.
+
+ // Check the number of operator parameters. Sometimes we have
+ // seen bad DWARF that doesn't correctly describe operators and
+ // if we try to create a method and add it to the class, clang
+ // will assert and crash, so we need to make sure things are
+ // acceptable.
+ clang::QualType method_qual_type(ClangUtil::GetQualType(function_clang_type));
+ const clang::FunctionProtoType *function_type =
+ llvm::dyn_cast<clang::FunctionProtoType>(method_qual_type.getTypePtr());
+ if (function_type == nullptr)
+ return clang::DeclarationName();
+
+ const bool is_method = false;
+ const unsigned int num_params = function_type->getNumParams();
+ if (!ClangASTContext::CheckOverloadedOperatorKindParameterCount(
+ is_method, op_kind, num_params))
+ return clang::DeclarationName();
+
+ return getASTContext()->DeclarationNames.getCXXOperatorName(op_kind);
+}
+
+FunctionDecl *ClangASTContext::CreateFunctionDeclaration(
+ DeclContext *decl_ctx, const char *name,
+ const CompilerType &function_clang_type, int storage, bool is_inline) {
+ FunctionDecl *func_decl = nullptr;
+ ASTContext *ast = getASTContext();
+ if (decl_ctx == nullptr)
+ decl_ctx = ast->getTranslationUnitDecl();
+
+ const bool hasWrittenPrototype = true;
+ const bool isConstexprSpecified = false;
+
+ clang::DeclarationName declarationName =
+ GetDeclarationName(name, function_clang_type);
+ func_decl = FunctionDecl::Create(
+ *ast, decl_ctx, SourceLocation(), SourceLocation(), declarationName,
+ ClangUtil::GetQualType(function_clang_type), nullptr,
+ (clang::StorageClass)storage, is_inline, hasWrittenPrototype,
+ isConstexprSpecified);
+ if (func_decl)
+ decl_ctx->addDecl(func_decl);
- clang::OverloadedOperatorKind op_kind = clang::NUM_OVERLOADED_OPERATORS;
- if (!IsOperator(name, op_kind) || op_kind == clang::NUM_OVERLOADED_OPERATORS)
- return DeclarationName(&getASTContext()->Idents.get(name)); // Not operator, but a regular function.
-
- // Check the number of operator parameters. Sometimes we have
- // seen bad DWARF that doesn't correctly describe operators and
- // if we try to create a method and add it to the class, clang
- // will assert and crash, so we need to make sure things are
- // acceptable.
- clang::QualType method_qual_type(ClangUtil::GetQualType(function_clang_type));
- const clang::FunctionProtoType *function_type =
- llvm::dyn_cast<clang::FunctionProtoType>(method_qual_type.getTypePtr());
- if (function_type == nullptr)
- return clang::DeclarationName();
-
- const bool is_method = false;
- const unsigned int num_params = function_type->getNumParams();
- if (!ClangASTContext::CheckOverloadedOperatorKindParameterCount(is_method, op_kind, num_params))
- return clang::DeclarationName();
-
- return getASTContext()->DeclarationNames.getCXXOperatorName(op_kind);
-}
-
-FunctionDecl *
-ClangASTContext::CreateFunctionDeclaration (DeclContext *decl_ctx,
- const char *name,
- const CompilerType &function_clang_type,
- int storage,
- bool is_inline)
-{
- FunctionDecl *func_decl = nullptr;
- ASTContext *ast = getASTContext();
- if (decl_ctx == nullptr)
- decl_ctx = ast->getTranslationUnitDecl();
-
-
- const bool hasWrittenPrototype = true;
- const bool isConstexprSpecified = false;
-
- clang::DeclarationName declarationName = GetDeclarationName(name, function_clang_type);
- func_decl = FunctionDecl::Create(*ast, decl_ctx, SourceLocation(), SourceLocation(), declarationName,
- ClangUtil::GetQualType(function_clang_type), nullptr, (clang::StorageClass)storage,
- is_inline, hasWrittenPrototype, isConstexprSpecified);
- if (func_decl)
- decl_ctx->addDecl (func_decl);
-
#ifdef LLDB_CONFIGURATION_DEBUG
- VerifyDecl(func_decl);
+ VerifyDecl(func_decl);
#endif
-
- return func_decl;
+
+ return func_decl;
+}
+
+CompilerType ClangASTContext::CreateFunctionType(
+ ASTContext *ast, const CompilerType &result_type, const CompilerType *args,
+ unsigned num_args, bool is_variadic, unsigned type_quals) {
+ if (ast == nullptr)
+ return CompilerType(); // invalid AST
+
+ if (!result_type || !ClangUtil::IsClangType(result_type))
+ return CompilerType(); // invalid return type
+
+ std::vector<QualType> qual_type_args;
+ if (num_args > 0 && args == nullptr)
+ return CompilerType(); // invalid argument array passed in
+
+ // Verify that all arguments are valid and the right type
+ for (unsigned i = 0; i < num_args; ++i) {
+ if (args[i]) {
+ // Make sure we have a clang type in args[i] and not a type from another
+ // language whose name might match
+ const bool is_clang_type = ClangUtil::IsClangType(args[i]);
+ lldbassert(is_clang_type);
+ if (is_clang_type)
+ qual_type_args.push_back(ClangUtil::GetQualType(args[i]));
+ else
+ return CompilerType(); // invalid argument type (must be a clang type)
+ } else
+ return CompilerType(); // invalid argument type (empty)
+ }
+
+ // TODO: Detect calling convention in DWARF?
+ FunctionProtoType::ExtProtoInfo proto_info;
+ proto_info.Variadic = is_variadic;
+ proto_info.ExceptionSpec = EST_None;
+ proto_info.TypeQuals = type_quals;
+ proto_info.RefQualifier = RQ_None;
+
+ return CompilerType(ast,
+ ast->getFunctionType(ClangUtil::GetQualType(result_type),
+ qual_type_args, proto_info));
+}
+
+ParmVarDecl *ClangASTContext::CreateParameterDeclaration(
+ const char *name, const CompilerType &param_type, int storage) {
+ ASTContext *ast = getASTContext();
+ assert(ast != nullptr);
+ return ParmVarDecl::Create(*ast, ast->getTranslationUnitDecl(),
+ SourceLocation(), SourceLocation(),
+ name && name[0] ? &ast->Idents.get(name) : nullptr,
+ ClangUtil::GetQualType(param_type), nullptr,
+ (clang::StorageClass)storage, nullptr);
+}
+
+void ClangASTContext::SetFunctionParameters(FunctionDecl *function_decl,
+ ParmVarDecl **params,
+ unsigned num_params) {
+ if (function_decl)
+ function_decl->setParams(ArrayRef<ParmVarDecl *>(params, num_params));
}
CompilerType
-ClangASTContext::CreateFunctionType (ASTContext *ast,
- const CompilerType& result_type,
- const CompilerType *args,
- unsigned num_args,
- bool is_variadic,
- unsigned type_quals)
-{
- if (ast == nullptr)
- return CompilerType(); // invalid AST
-
- if (!result_type || !ClangUtil::IsClangType(result_type))
- return CompilerType(); // invalid return type
-
- std::vector<QualType> qual_type_args;
- if (num_args > 0 && args == nullptr)
- return CompilerType(); // invalid argument array passed in
-
- // Verify that all arguments are valid and the right type
- for (unsigned i=0; i<num_args; ++i)
- {
- if (args[i])
- {
- // Make sure we have a clang type in args[i] and not a type from another
- // language whose name might match
- const bool is_clang_type = ClangUtil::IsClangType(args[i]);
- lldbassert(is_clang_type);
- if (is_clang_type)
- qual_type_args.push_back(ClangUtil::GetQualType(args[i]));
- else
- return CompilerType(); // invalid argument type (must be a clang type)
- }
- else
- return CompilerType(); // invalid argument type (empty)
- }
+ClangASTContext::CreateBlockPointerType(const CompilerType &function_type) {
+ QualType block_type = m_ast_ap->getBlockPointerType(
+ clang::QualType::getFromOpaquePtr(function_type.GetOpaqueQualType()));
- // TODO: Detect calling convention in DWARF?
- FunctionProtoType::ExtProtoInfo proto_info;
- proto_info.Variadic = is_variadic;
- proto_info.ExceptionSpec = EST_None;
- proto_info.TypeQuals = type_quals;
- proto_info.RefQualifier = RQ_None;
-
- return CompilerType(ast, ast->getFunctionType(ClangUtil::GetQualType(result_type), qual_type_args, proto_info));
+ return CompilerType(this, block_type.getAsOpaquePtr());
}
-ParmVarDecl *
-ClangASTContext::CreateParameterDeclaration (const char *name, const CompilerType &param_type, int storage)
-{
- ASTContext *ast = getASTContext();
- assert (ast != nullptr);
- return ParmVarDecl::Create(*ast, ast->getTranslationUnitDecl(), SourceLocation(), SourceLocation(),
- name && name[0] ? &ast->Idents.get(name) : nullptr, ClangUtil::GetQualType(param_type),
- nullptr, (clang::StorageClass)storage, nullptr);
-}
+#pragma mark Array Types
-void
-ClangASTContext::SetFunctionParameters (FunctionDecl *function_decl, ParmVarDecl **params, unsigned num_params)
-{
- if (function_decl)
- function_decl->setParams (ArrayRef<ParmVarDecl*>(params, num_params));
-}
+CompilerType ClangASTContext::CreateArrayType(const CompilerType &element_type,
+ size_t element_count,
+ bool is_vector) {
+ if (element_type.IsValid()) {
+ ASTContext *ast = getASTContext();
+ assert(ast != nullptr);
+
+ if (is_vector) {
+ return CompilerType(
+ ast, ast->getExtVectorType(ClangUtil::GetQualType(element_type),
+ element_count));
+ } else {
+
+ llvm::APInt ap_element_count(64, element_count);
+ if (element_count == 0) {
+ return CompilerType(ast, ast->getIncompleteArrayType(
+ ClangUtil::GetQualType(element_type),
+ clang::ArrayType::Normal, 0));
+ } else {
+ return CompilerType(
+ ast, ast->getConstantArrayType(ClangUtil::GetQualType(element_type),
+ ap_element_count,
+ clang::ArrayType::Normal, 0));
+ }
+ }
+ }
+ return CompilerType();
+}
+
+CompilerType ClangASTContext::CreateStructForIdentifier(
+ const ConstString &type_name,
+ const std::initializer_list<std::pair<const char *, CompilerType>>
+ &type_fields,
+ bool packed) {
+ CompilerType type;
+ if (!type_name.IsEmpty() &&
+ (type = GetTypeForIdentifier<clang::CXXRecordDecl>(type_name))
+ .IsValid()) {
+ lldbassert("Trying to create a type for an existing name");
+ return type;
+ }
+
+ type = CreateRecordType(nullptr, lldb::eAccessPublic, type_name.GetCString(),
+ clang::TTK_Struct, lldb::eLanguageTypeC);
+ StartTagDeclarationDefinition(type);
+ for (const auto &field : type_fields)
+ AddFieldToRecordType(type, field.first, field.second, lldb::eAccessPublic,
+ 0);
+ if (packed)
+ SetIsPacked(type);
+ CompleteTagDeclarationDefinition(type);
+ return type;
+}
+
+CompilerType ClangASTContext::GetOrCreateStructForIdentifier(
+ const ConstString &type_name,
+ const std::initializer_list<std::pair<const char *, CompilerType>>
+ &type_fields,
+ bool packed) {
+ CompilerType type;
+ if ((type = GetTypeForIdentifier<clang::CXXRecordDecl>(type_name)).IsValid())
+ return type;
-CompilerType
-ClangASTContext::CreateBlockPointerType (const CompilerType &function_type)
-{
- QualType block_type = m_ast_ap->getBlockPointerType(clang::QualType::getFromOpaquePtr(function_type.GetOpaqueQualType()));
-
- return CompilerType (this, block_type.getAsOpaquePtr());
+ return CreateStructForIdentifier(type_name, type_fields, packed);
}
-#pragma mark Array Types
-
-CompilerType
-ClangASTContext::CreateArrayType (const CompilerType &element_type,
- size_t element_count,
- bool is_vector)
-{
- if (element_type.IsValid())
- {
- ASTContext *ast = getASTContext();
- assert (ast != nullptr);
-
- if (is_vector)
- {
- return CompilerType(ast, ast->getExtVectorType(ClangUtil::GetQualType(element_type), element_count));
- }
- else
- {
-
- llvm::APInt ap_element_count (64, element_count);
- if (element_count == 0)
- {
- return CompilerType(ast, ast->getIncompleteArrayType(ClangUtil::GetQualType(element_type),
- clang::ArrayType::Normal, 0));
- }
- else
- {
- return CompilerType(ast, ast->getConstantArrayType(ClangUtil::GetQualType(element_type),
- ap_element_count, clang::ArrayType::Normal, 0));
- }
- }
- }
- return CompilerType();
-}
+#pragma mark Enumeration Types
CompilerType
-ClangASTContext::CreateStructForIdentifier (const ConstString &type_name,
- const std::initializer_list< std::pair < const char *, CompilerType > >& type_fields,
- bool packed)
-{
- CompilerType type;
- if (!type_name.IsEmpty() && (type = GetTypeForIdentifier<clang::CXXRecordDecl>(type_name)).IsValid())
- {
- lldbassert("Trying to create a type for an existing name");
- return type;
- }
-
- type = CreateRecordType(nullptr, lldb::eAccessPublic, type_name.GetCString(), clang::TTK_Struct, lldb::eLanguageTypeC);
- StartTagDeclarationDefinition(type);
- for (const auto& field : type_fields)
- AddFieldToRecordType(type, field.first, field.second, lldb::eAccessPublic, 0);
- if (packed)
- SetIsPacked(type);
- CompleteTagDeclarationDefinition(type);
- return type;
-}
+ClangASTContext::CreateEnumerationType(const char *name, DeclContext *decl_ctx,
+ const Declaration &decl,
+ const CompilerType &integer_clang_type) {
+ // TODO: Do something intelligent with the Declaration object passed in
+ // like maybe filling in the SourceLocation with it...
+ ASTContext *ast = getASTContext();
-CompilerType
-ClangASTContext::GetOrCreateStructForIdentifier (const ConstString &type_name,
- const std::initializer_list< std::pair < const char *, CompilerType > >& type_fields,
- bool packed)
-{
- CompilerType type;
- if ((type = GetTypeForIdentifier<clang::CXXRecordDecl>(type_name)).IsValid())
- return type;
+ // TODO: ask about these...
+ // const bool IsScoped = false;
+ // const bool IsFixed = false;
- return CreateStructForIdentifier (type_name,
- type_fields,
- packed);
-}
+ EnumDecl *enum_decl = EnumDecl::Create(
+ *ast, decl_ctx, SourceLocation(), SourceLocation(),
+ name && name[0] ? &ast->Idents.get(name) : nullptr, nullptr,
+ false, // IsScoped
+ false, // IsScopedUsingClassTag
+ false); // IsFixed
-#pragma mark Enumeration Types
+ if (enum_decl) {
+ // TODO: check if we should be setting the promotion type too?
+ enum_decl->setIntegerType(ClangUtil::GetQualType(integer_clang_type));
-CompilerType
-ClangASTContext::CreateEnumerationType
-(
- const char *name,
- DeclContext *decl_ctx,
- const Declaration &decl,
- const CompilerType &integer_clang_type
- )
-{
- // TODO: Do something intelligent with the Declaration object passed in
- // like maybe filling in the SourceLocation with it...
- ASTContext *ast = getASTContext();
-
- // TODO: ask about these...
- // const bool IsScoped = false;
- // const bool IsFixed = false;
-
- EnumDecl *enum_decl = EnumDecl::Create (*ast,
- decl_ctx,
- SourceLocation(),
- SourceLocation(),
- name && name[0] ? &ast->Idents.get(name) : nullptr,
- nullptr,
- false, // IsScoped
- false, // IsScopedUsingClassTag
- false); // IsFixed
-
-
- if (enum_decl)
- {
- // TODO: check if we should be setting the promotion type too?
- enum_decl->setIntegerType(ClangUtil::GetQualType(integer_clang_type));
+ enum_decl->setAccess(AS_public); // TODO respect what's in the debug info
- enum_decl->setAccess(AS_public); // TODO respect what's in the debug info
-
- return CompilerType (ast, ast->getTagDeclType(enum_decl));
- }
- return CompilerType();
+ return CompilerType(ast, ast->getTagDeclType(enum_decl));
+ }
+ return CompilerType();
}
// Disable this for now since I can't seem to get a nicely formatted float
@@ -2455,8 +2177,10 @@ ClangASTContext::CreateEnumerationType
// would like to get perfect string values for any kind of float semantics
// so we can support remote targets. The code below also requires a patch to
// llvm::APInt.
-//bool
-//ClangASTContext::ConvertFloatValueToString (ASTContext *ast, lldb::opaque_compiler_type_t clang_type, const uint8_t* bytes, size_t byte_size, int apint_byte_order, std::string &float_str)
+// bool
+// ClangASTContext::ConvertFloatValueToString (ASTContext *ast,
+// lldb::opaque_compiler_type_t clang_type, const uint8_t* bytes, size_t
+// byte_size, int apint_byte_order, std::string &float_str)
//{
// uint32_t count = 0;
// bool is_complex = false;
@@ -2469,14 +2193,16 @@ ClangASTContext::CreateEnumerationType
// uint32_t i;
// for (i=0; i<count; i++)
// {
-// APInt ap_int(num_bits_per_float, bytes + i * num_bytes_per_float, (APInt::ByteOrder)apint_byte_order);
+// APInt ap_int(num_bits_per_float, bytes + i * num_bytes_per_float,
+// (APInt::ByteOrder)apint_byte_order);
// bool is_ieee = false;
// APFloat ap_float(ap_int, is_ieee);
// char s[1024];
// unsigned int hex_digits = 0;
// bool upper_case = false;
//
-// if (ap_float.convertToHexString(s, hex_digits, upper_case, APFloat::rmNearestTiesToEven) > 0)
+// if (ap_float.convertToHexString(s, hex_digits, upper_case,
+// APFloat::rmNearestTiesToEven) > 0)
// {
// if (i > 0)
// float_str.append(", ");
@@ -2490,2051 +2216,2116 @@ ClangASTContext::CreateEnumerationType
// return false;
//}
-CompilerType
-ClangASTContext::GetIntTypeFromBitSize (clang::ASTContext *ast,
- size_t bit_size, bool is_signed)
-{
- if (ast)
- {
- if (is_signed)
- {
- if (bit_size == ast->getTypeSize(ast->SignedCharTy))
- return CompilerType(ast, ast->SignedCharTy);
-
- if (bit_size == ast->getTypeSize(ast->ShortTy))
- return CompilerType(ast, ast->ShortTy);
-
- if (bit_size == ast->getTypeSize(ast->IntTy))
- return CompilerType(ast, ast->IntTy);
-
- if (bit_size == ast->getTypeSize(ast->LongTy))
- return CompilerType(ast, ast->LongTy);
-
- if (bit_size == ast->getTypeSize(ast->LongLongTy))
- return CompilerType(ast, ast->LongLongTy);
-
- if (bit_size == ast->getTypeSize(ast->Int128Ty))
- return CompilerType(ast, ast->Int128Ty);
+CompilerType ClangASTContext::GetIntTypeFromBitSize(clang::ASTContext *ast,
+ size_t bit_size,
+ bool is_signed) {
+ if (ast) {
+ if (is_signed) {
+ if (bit_size == ast->getTypeSize(ast->SignedCharTy))
+ return CompilerType(ast, ast->SignedCharTy);
+
+ if (bit_size == ast->getTypeSize(ast->ShortTy))
+ return CompilerType(ast, ast->ShortTy);
+
+ if (bit_size == ast->getTypeSize(ast->IntTy))
+ return CompilerType(ast, ast->IntTy);
+
+ if (bit_size == ast->getTypeSize(ast->LongTy))
+ return CompilerType(ast, ast->LongTy);
+
+ if (bit_size == ast->getTypeSize(ast->LongLongTy))
+ return CompilerType(ast, ast->LongLongTy);
+
+ if (bit_size == ast->getTypeSize(ast->Int128Ty))
+ return CompilerType(ast, ast->Int128Ty);
+ } else {
+ if (bit_size == ast->getTypeSize(ast->UnsignedCharTy))
+ return CompilerType(ast, ast->UnsignedCharTy);
+
+ if (bit_size == ast->getTypeSize(ast->UnsignedShortTy))
+ return CompilerType(ast, ast->UnsignedShortTy);
+
+ if (bit_size == ast->getTypeSize(ast->UnsignedIntTy))
+ return CompilerType(ast, ast->UnsignedIntTy);
+
+ if (bit_size == ast->getTypeSize(ast->UnsignedLongTy))
+ return CompilerType(ast, ast->UnsignedLongTy);
+
+ if (bit_size == ast->getTypeSize(ast->UnsignedLongLongTy))
+ return CompilerType(ast, ast->UnsignedLongLongTy);
+
+ if (bit_size == ast->getTypeSize(ast->UnsignedInt128Ty))
+ return CompilerType(ast, ast->UnsignedInt128Ty);
+ }
+ }
+ return CompilerType();
+}
+
+CompilerType ClangASTContext::GetPointerSizedIntType(clang::ASTContext *ast,
+ bool is_signed) {
+ if (ast)
+ return GetIntTypeFromBitSize(ast, ast->getTypeSize(ast->VoidPtrTy),
+ is_signed);
+ return CompilerType();
+}
+
+void ClangASTContext::DumpDeclContextHiearchy(clang::DeclContext *decl_ctx) {
+ if (decl_ctx) {
+ DumpDeclContextHiearchy(decl_ctx->getParent());
+
+ clang::NamedDecl *named_decl = llvm::dyn_cast<clang::NamedDecl>(decl_ctx);
+ if (named_decl) {
+ printf("%20s: %s\n", decl_ctx->getDeclKindName(),
+ named_decl->getDeclName().getAsString().c_str());
+ } else {
+ printf("%20s\n", decl_ctx->getDeclKindName());
+ }
+ }
+}
+
+void ClangASTContext::DumpDeclHiearchy(clang::Decl *decl) {
+ if (decl == nullptr)
+ return;
+ DumpDeclContextHiearchy(decl->getDeclContext());
+
+ clang::RecordDecl *record_decl = llvm::dyn_cast<clang::RecordDecl>(decl);
+ if (record_decl) {
+ printf("%20s: %s%s\n", decl->getDeclKindName(),
+ record_decl->getDeclName().getAsString().c_str(),
+ record_decl->isInjectedClassName() ? " (injected class name)" : "");
+
+ } else {
+ clang::NamedDecl *named_decl = llvm::dyn_cast<clang::NamedDecl>(decl);
+ if (named_decl) {
+ printf("%20s: %s\n", decl->getDeclKindName(),
+ named_decl->getDeclName().getAsString().c_str());
+ } else {
+ printf("%20s\n", decl->getDeclKindName());
+ }
+ }
+}
+
+bool ClangASTContext::DeclsAreEquivalent(clang::Decl *lhs_decl,
+ clang::Decl *rhs_decl) {
+ if (lhs_decl && rhs_decl) {
+ //----------------------------------------------------------------------
+ // Make sure the decl kinds match first
+ //----------------------------------------------------------------------
+ const clang::Decl::Kind lhs_decl_kind = lhs_decl->getKind();
+ const clang::Decl::Kind rhs_decl_kind = rhs_decl->getKind();
+
+ if (lhs_decl_kind == rhs_decl_kind) {
+ //------------------------------------------------------------------
+ // Now check that the decl contexts kinds are all equivalent
+ // before we have to check any names of the decl contexts...
+ //------------------------------------------------------------------
+ clang::DeclContext *lhs_decl_ctx = lhs_decl->getDeclContext();
+ clang::DeclContext *rhs_decl_ctx = rhs_decl->getDeclContext();
+ if (lhs_decl_ctx && rhs_decl_ctx) {
+ while (1) {
+ if (lhs_decl_ctx && rhs_decl_ctx) {
+ const clang::Decl::Kind lhs_decl_ctx_kind =
+ lhs_decl_ctx->getDeclKind();
+ const clang::Decl::Kind rhs_decl_ctx_kind =
+ rhs_decl_ctx->getDeclKind();
+ if (lhs_decl_ctx_kind == rhs_decl_ctx_kind) {
+ lhs_decl_ctx = lhs_decl_ctx->getParent();
+ rhs_decl_ctx = rhs_decl_ctx->getParent();
+
+ if (lhs_decl_ctx == nullptr && rhs_decl_ctx == nullptr)
+ break;
+ } else
+ return false;
+ } else
+ return false;
}
- else
- {
- if (bit_size == ast->getTypeSize(ast->UnsignedCharTy))
- return CompilerType(ast, ast->UnsignedCharTy);
-
- if (bit_size == ast->getTypeSize(ast->UnsignedShortTy))
- return CompilerType(ast, ast->UnsignedShortTy);
-
- if (bit_size == ast->getTypeSize(ast->UnsignedIntTy))
- return CompilerType(ast, ast->UnsignedIntTy);
-
- if (bit_size == ast->getTypeSize(ast->UnsignedLongTy))
- return CompilerType(ast, ast->UnsignedLongTy);
-
- if (bit_size == ast->getTypeSize(ast->UnsignedLongLongTy))
- return CompilerType(ast, ast->UnsignedLongLongTy);
-
- if (bit_size == ast->getTypeSize(ast->UnsignedInt128Ty))
- return CompilerType(ast, ast->UnsignedInt128Ty);
+
+ //--------------------------------------------------------------
+ // Now make sure the name of the decls match
+ //--------------------------------------------------------------
+ clang::NamedDecl *lhs_named_decl =
+ llvm::dyn_cast<clang::NamedDecl>(lhs_decl);
+ clang::NamedDecl *rhs_named_decl =
+ llvm::dyn_cast<clang::NamedDecl>(rhs_decl);
+ if (lhs_named_decl && rhs_named_decl) {
+ clang::DeclarationName lhs_decl_name = lhs_named_decl->getDeclName();
+ clang::DeclarationName rhs_decl_name = rhs_named_decl->getDeclName();
+ if (lhs_decl_name.getNameKind() == rhs_decl_name.getNameKind()) {
+ if (lhs_decl_name.getAsString() != rhs_decl_name.getAsString())
+ return false;
+ } else
+ return false;
+ } else
+ return false;
+
+ //--------------------------------------------------------------
+ // We know that the decl context kinds all match, so now we need
+ // to make sure the names match as well
+ //--------------------------------------------------------------
+ lhs_decl_ctx = lhs_decl->getDeclContext();
+ rhs_decl_ctx = rhs_decl->getDeclContext();
+ while (1) {
+ switch (lhs_decl_ctx->getDeclKind()) {
+ case clang::Decl::TranslationUnit:
+ // We don't care about the translation unit names
+ return true;
+ default: {
+ clang::NamedDecl *lhs_named_decl =
+ llvm::dyn_cast<clang::NamedDecl>(lhs_decl_ctx);
+ clang::NamedDecl *rhs_named_decl =
+ llvm::dyn_cast<clang::NamedDecl>(rhs_decl_ctx);
+ if (lhs_named_decl && rhs_named_decl) {
+ clang::DeclarationName lhs_decl_name =
+ lhs_named_decl->getDeclName();
+ clang::DeclarationName rhs_decl_name =
+ rhs_named_decl->getDeclName();
+ if (lhs_decl_name.getNameKind() == rhs_decl_name.getNameKind()) {
+ if (lhs_decl_name.getAsString() != rhs_decl_name.getAsString())
+ return false;
+ } else
+ return false;
+ } else
+ return false;
+ } break;
+ }
+ lhs_decl_ctx = lhs_decl_ctx->getParent();
+ rhs_decl_ctx = rhs_decl_ctx->getParent();
}
+ }
}
- return CompilerType();
+ }
+ return false;
}
+bool ClangASTContext::GetCompleteDecl(clang::ASTContext *ast,
+ clang::Decl *decl) {
+ if (!decl)
+ return false;
-CompilerType
-ClangASTContext::GetPointerSizedIntType (clang::ASTContext *ast, bool is_signed)
-{
- if (ast)
- return GetIntTypeFromBitSize(ast, ast->getTypeSize(ast->VoidPtrTy), is_signed);
- return CompilerType();
-}
+ ExternalASTSource *ast_source = ast->getExternalSource();
-void
-ClangASTContext::DumpDeclContextHiearchy (clang::DeclContext *decl_ctx)
-{
- if (decl_ctx)
- {
- DumpDeclContextHiearchy (decl_ctx->getParent());
+ if (!ast_source)
+ return false;
- clang::NamedDecl *named_decl = llvm::dyn_cast<clang::NamedDecl>(decl_ctx);
- if (named_decl)
- {
- printf ("%20s: %s\n", decl_ctx->getDeclKindName(), named_decl->getDeclName().getAsString().c_str());
- }
- else
- {
- printf ("%20s\n", decl_ctx->getDeclKindName());
- }
- }
-}
+ if (clang::TagDecl *tag_decl = llvm::dyn_cast<clang::TagDecl>(decl)) {
+ if (tag_decl->isCompleteDefinition())
+ return true;
-void
-ClangASTContext::DumpDeclHiearchy (clang::Decl *decl)
-{
- if (decl == nullptr)
- return;
- DumpDeclContextHiearchy(decl->getDeclContext());
+ if (!tag_decl->hasExternalLexicalStorage())
+ return false;
- clang::RecordDecl *record_decl = llvm::dyn_cast<clang::RecordDecl>(decl);
- if (record_decl)
- {
- printf ("%20s: %s%s\n", decl->getDeclKindName(), record_decl->getDeclName().getAsString().c_str(), record_decl->isInjectedClassName() ? " (injected class name)" : "");
+ ast_source->CompleteType(tag_decl);
- }
- else
- {
- clang::NamedDecl *named_decl = llvm::dyn_cast<clang::NamedDecl>(decl);
- if (named_decl)
- {
- printf ("%20s: %s\n", decl->getDeclKindName(), named_decl->getDeclName().getAsString().c_str());
- }
- else
- {
- printf ("%20s\n", decl->getDeclKindName());
- }
- }
-}
+ return !tag_decl->getTypeForDecl()->isIncompleteType();
+ } else if (clang::ObjCInterfaceDecl *objc_interface_decl =
+ llvm::dyn_cast<clang::ObjCInterfaceDecl>(decl)) {
+ if (objc_interface_decl->getDefinition())
+ return true;
-bool
-ClangASTContext::DeclsAreEquivalent (clang::Decl *lhs_decl, clang::Decl *rhs_decl)
-{
- if (lhs_decl && rhs_decl)
- {
- //----------------------------------------------------------------------
- // Make sure the decl kinds match first
- //----------------------------------------------------------------------
- const clang::Decl::Kind lhs_decl_kind = lhs_decl->getKind();
- const clang::Decl::Kind rhs_decl_kind = rhs_decl->getKind();
-
- if (lhs_decl_kind == rhs_decl_kind)
- {
- //------------------------------------------------------------------
- // Now check that the decl contexts kinds are all equivalent
- // before we have to check any names of the decl contexts...
- //------------------------------------------------------------------
- clang::DeclContext *lhs_decl_ctx = lhs_decl->getDeclContext();
- clang::DeclContext *rhs_decl_ctx = rhs_decl->getDeclContext();
- if (lhs_decl_ctx && rhs_decl_ctx)
- {
- while (1)
- {
- if (lhs_decl_ctx && rhs_decl_ctx)
- {
- const clang::Decl::Kind lhs_decl_ctx_kind = lhs_decl_ctx->getDeclKind();
- const clang::Decl::Kind rhs_decl_ctx_kind = rhs_decl_ctx->getDeclKind();
- if (lhs_decl_ctx_kind == rhs_decl_ctx_kind)
- {
- lhs_decl_ctx = lhs_decl_ctx->getParent();
- rhs_decl_ctx = rhs_decl_ctx->getParent();
-
- if (lhs_decl_ctx == nullptr && rhs_decl_ctx == nullptr)
- break;
- }
- else
- return false;
- }
- else
- return false;
- }
+ if (!objc_interface_decl->hasExternalLexicalStorage())
+ return false;
- //--------------------------------------------------------------
- // Now make sure the name of the decls match
- //--------------------------------------------------------------
- clang::NamedDecl *lhs_named_decl = llvm::dyn_cast<clang::NamedDecl>(lhs_decl);
- clang::NamedDecl *rhs_named_decl = llvm::dyn_cast<clang::NamedDecl>(rhs_decl);
- if (lhs_named_decl && rhs_named_decl)
- {
- clang::DeclarationName lhs_decl_name = lhs_named_decl->getDeclName();
- clang::DeclarationName rhs_decl_name = rhs_named_decl->getDeclName();
- if (lhs_decl_name.getNameKind() == rhs_decl_name.getNameKind())
- {
- if (lhs_decl_name.getAsString() != rhs_decl_name.getAsString())
- return false;
- }
- else
- return false;
- }
- else
- return false;
-
- //--------------------------------------------------------------
- // We know that the decl context kinds all match, so now we need
- // to make sure the names match as well
- //--------------------------------------------------------------
- lhs_decl_ctx = lhs_decl->getDeclContext();
- rhs_decl_ctx = rhs_decl->getDeclContext();
- while (1)
- {
- switch (lhs_decl_ctx->getDeclKind())
- {
- case clang::Decl::TranslationUnit:
- // We don't care about the translation unit names
- return true;
- default:
- {
- clang::NamedDecl *lhs_named_decl = llvm::dyn_cast<clang::NamedDecl>(lhs_decl_ctx);
- clang::NamedDecl *rhs_named_decl = llvm::dyn_cast<clang::NamedDecl>(rhs_decl_ctx);
- if (lhs_named_decl && rhs_named_decl)
- {
- clang::DeclarationName lhs_decl_name = lhs_named_decl->getDeclName();
- clang::DeclarationName rhs_decl_name = rhs_named_decl->getDeclName();
- if (lhs_decl_name.getNameKind() == rhs_decl_name.getNameKind())
- {
- if (lhs_decl_name.getAsString() != rhs_decl_name.getAsString())
- return false;
- }
- else
- return false;
- }
- else
- return false;
- }
- break;
+ ast_source->CompleteType(objc_interface_decl);
- }
- lhs_decl_ctx = lhs_decl_ctx->getParent();
- rhs_decl_ctx = rhs_decl_ctx->getParent();
- }
- }
- }
- }
+ return !objc_interface_decl->getTypeForDecl()->isIncompleteType();
+ } else {
return false;
-}
-bool
-ClangASTContext::GetCompleteDecl (clang::ASTContext *ast,
- clang::Decl *decl)
-{
- if (!decl)
- return false;
-
- ExternalASTSource *ast_source = ast->getExternalSource();
-
- if (!ast_source)
- return false;
-
- if (clang::TagDecl *tag_decl = llvm::dyn_cast<clang::TagDecl>(decl))
- {
- if (tag_decl->isCompleteDefinition())
- return true;
-
- if (!tag_decl->hasExternalLexicalStorage())
- return false;
-
- ast_source->CompleteType(tag_decl);
-
- return !tag_decl->getTypeForDecl()->isIncompleteType();
- }
- else if (clang::ObjCInterfaceDecl *objc_interface_decl = llvm::dyn_cast<clang::ObjCInterfaceDecl>(decl))
- {
- if (objc_interface_decl->getDefinition())
- return true;
-
- if (!objc_interface_decl->hasExternalLexicalStorage())
- return false;
-
- ast_source->CompleteType(objc_interface_decl);
-
- return !objc_interface_decl->getTypeForDecl()->isIncompleteType();
- }
- else
- {
- return false;
- }
+ }
}
-void
-ClangASTContext::SetMetadataAsUserID (const void *object,
- user_id_t user_id)
-{
- ClangASTMetadata meta_data;
- meta_data.SetUserID (user_id);
- SetMetadata (object, meta_data);
+void ClangASTContext::SetMetadataAsUserID(const void *object,
+ user_id_t user_id) {
+ ClangASTMetadata meta_data;
+ meta_data.SetUserID(user_id);
+ SetMetadata(object, meta_data);
}
-void
-ClangASTContext::SetMetadata (clang::ASTContext *ast,
- const void *object,
- ClangASTMetadata &metadata)
-{
- ClangExternalASTSourceCommon *external_source =
- ClangExternalASTSourceCommon::Lookup(ast->getExternalSource());
-
- if (external_source)
- external_source->SetMetadata(object, metadata);
-}
+void ClangASTContext::SetMetadata(clang::ASTContext *ast, const void *object,
+ ClangASTMetadata &metadata) {
+ ClangExternalASTSourceCommon *external_source =
+ ClangExternalASTSourceCommon::Lookup(ast->getExternalSource());
-ClangASTMetadata *
-ClangASTContext::GetMetadata (clang::ASTContext *ast,
- const void *object)
-{
- ClangExternalASTSourceCommon *external_source =
- ClangExternalASTSourceCommon::Lookup(ast->getExternalSource());
-
- if (external_source && external_source->HasMetadata(object))
- return external_source->GetMetadata(object);
- else
- return nullptr;
+ if (external_source)
+ external_source->SetMetadata(object, metadata);
}
-clang::DeclContext *
-ClangASTContext::GetAsDeclContext (clang::CXXMethodDecl *cxx_method_decl)
-{
- return llvm::dyn_cast<clang::DeclContext>(cxx_method_decl);
+ClangASTMetadata *ClangASTContext::GetMetadata(clang::ASTContext *ast,
+ const void *object) {
+ ClangExternalASTSourceCommon *external_source =
+ ClangExternalASTSourceCommon::Lookup(ast->getExternalSource());
+
+ if (external_source && external_source->HasMetadata(object))
+ return external_source->GetMetadata(object);
+ else
+ return nullptr;
}
clang::DeclContext *
-ClangASTContext::GetAsDeclContext (clang::ObjCMethodDecl *objc_method_decl)
-{
- return llvm::dyn_cast<clang::DeclContext>(objc_method_decl);
+ClangASTContext::GetAsDeclContext(clang::CXXMethodDecl *cxx_method_decl) {
+ return llvm::dyn_cast<clang::DeclContext>(cxx_method_decl);
}
-bool
-ClangASTContext::SetTagTypeKind (clang::QualType tag_qual_type, int kind) const
-{
- const clang::Type *clang_type = tag_qual_type.getTypePtr();
- if (clang_type)
- {
- const clang::TagType *tag_type = llvm::dyn_cast<clang::TagType>(clang_type);
- if (tag_type)
- {
- clang::TagDecl *tag_decl = llvm::dyn_cast<clang::TagDecl>(tag_type->getDecl());
- if (tag_decl)
- {
- tag_decl->setTagKind ((clang::TagDecl::TagKind)kind);
- return true;
- }
- }
+clang::DeclContext *
+ClangASTContext::GetAsDeclContext(clang::ObjCMethodDecl *objc_method_decl) {
+ return llvm::dyn_cast<clang::DeclContext>(objc_method_decl);
+}
+
+bool ClangASTContext::SetTagTypeKind(clang::QualType tag_qual_type,
+ int kind) const {
+ const clang::Type *clang_type = tag_qual_type.getTypePtr();
+ if (clang_type) {
+ const clang::TagType *tag_type = llvm::dyn_cast<clang::TagType>(clang_type);
+ if (tag_type) {
+ clang::TagDecl *tag_decl =
+ llvm::dyn_cast<clang::TagDecl>(tag_type->getDecl());
+ if (tag_decl) {
+ tag_decl->setTagKind((clang::TagDecl::TagKind)kind);
+ return true;
+ }
}
- return false;
+ }
+ return false;
}
-
-bool
-ClangASTContext::SetDefaultAccessForRecordFields (clang::RecordDecl* record_decl,
- int default_accessibility,
- int *assigned_accessibilities,
- size_t num_assigned_accessibilities)
-{
- if (record_decl)
- {
- uint32_t field_idx;
- clang::RecordDecl::field_iterator field, field_end;
- for (field = record_decl->field_begin(), field_end = record_decl->field_end(), field_idx = 0;
- field != field_end;
- ++field, ++field_idx)
- {
- // If no accessibility was assigned, assign the correct one
- if (field_idx < num_assigned_accessibilities && assigned_accessibilities[field_idx] == clang::AS_none)
- field->setAccess ((clang::AccessSpecifier)default_accessibility);
- }
- return true;
+bool ClangASTContext::SetDefaultAccessForRecordFields(
+ clang::RecordDecl *record_decl, int default_accessibility,
+ int *assigned_accessibilities, size_t num_assigned_accessibilities) {
+ if (record_decl) {
+ uint32_t field_idx;
+ clang::RecordDecl::field_iterator field, field_end;
+ for (field = record_decl->field_begin(),
+ field_end = record_decl->field_end(), field_idx = 0;
+ field != field_end; ++field, ++field_idx) {
+ // If no accessibility was assigned, assign the correct one
+ if (field_idx < num_assigned_accessibilities &&
+ assigned_accessibilities[field_idx] == clang::AS_none)
+ field->setAccess((clang::AccessSpecifier)default_accessibility);
}
- return false;
+ return true;
+ }
+ return false;
}
clang::DeclContext *
-ClangASTContext::GetDeclContextForType (const CompilerType& type)
-{
- return GetDeclContextForType(ClangUtil::GetQualType(type));
+ClangASTContext::GetDeclContextForType(const CompilerType &type) {
+ return GetDeclContextForType(ClangUtil::GetQualType(type));
}
clang::DeclContext *
-ClangASTContext::GetDeclContextForType (clang::QualType type)
-{
- if (type.isNull())
- return nullptr;
-
- clang::QualType qual_type = type.getCanonicalType();
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::ObjCInterface: return llvm::cast<clang::ObjCObjectType>(qual_type.getTypePtr())->getInterface();
- case clang::Type::ObjCObjectPointer: return GetDeclContextForType (llvm::cast<clang::ObjCObjectPointerType>(qual_type.getTypePtr())->getPointeeType());
- case clang::Type::Record: return llvm::cast<clang::RecordType>(qual_type)->getDecl();
- case clang::Type::Enum: return llvm::cast<clang::EnumType>(qual_type)->getDecl();
- case clang::Type::Typedef: return GetDeclContextForType (llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType());
- case clang::Type::Auto: return GetDeclContextForType (llvm::cast<clang::AutoType>(qual_type)->getDeducedType());
- case clang::Type::Elaborated: return GetDeclContextForType (llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType());
- case clang::Type::Paren: return GetDeclContextForType (llvm::cast<clang::ParenType>(qual_type)->desugar());
- default:
- break;
- }
- // No DeclContext in this type...
+ClangASTContext::GetDeclContextForType(clang::QualType type) {
+ if (type.isNull())
return nullptr;
-}
-static bool
-GetCompleteQualType (clang::ASTContext *ast, clang::QualType qual_type, bool allow_completion = true)
-{
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::ConstantArray:
- case clang::Type::IncompleteArray:
- case clang::Type::VariableArray:
- {
- const clang::ArrayType *array_type = llvm::dyn_cast<clang::ArrayType>(qual_type.getTypePtr());
-
- if (array_type)
- return GetCompleteQualType (ast, array_type->getElementType(), allow_completion);
- }
- break;
- case clang::Type::Record:
- {
- clang::CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
- if (cxx_record_decl)
- {
- if (cxx_record_decl->hasExternalLexicalStorage())
- {
- const bool is_complete = cxx_record_decl->isCompleteDefinition();
- const bool fields_loaded = cxx_record_decl->hasLoadedFieldsFromExternalStorage();
- if (is_complete && fields_loaded)
- return true;
-
- if (!allow_completion)
- return false;
-
- // Call the field_begin() accessor to for it to use the external source
- // to load the fields...
- clang::ExternalASTSource *external_ast_source = ast->getExternalSource();
- if (external_ast_source)
- {
- external_ast_source->CompleteType(cxx_record_decl);
- if (cxx_record_decl->isCompleteDefinition())
- {
- cxx_record_decl->field_begin();
- cxx_record_decl->setHasLoadedFieldsFromExternalStorage (true);
- }
- }
- }
- }
- const clang::TagType *tag_type = llvm::cast<clang::TagType>(qual_type.getTypePtr());
- return !tag_type->isIncompleteType();
+ clang::QualType qual_type = type.getCanonicalType();
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::ObjCInterface:
+ return llvm::cast<clang::ObjCObjectType>(qual_type.getTypePtr())
+ ->getInterface();
+ case clang::Type::ObjCObjectPointer:
+ return GetDeclContextForType(
+ llvm::cast<clang::ObjCObjectPointerType>(qual_type.getTypePtr())
+ ->getPointeeType());
+ case clang::Type::Record:
+ return llvm::cast<clang::RecordType>(qual_type)->getDecl();
+ case clang::Type::Enum:
+ return llvm::cast<clang::EnumType>(qual_type)->getDecl();
+ case clang::Type::Typedef:
+ return GetDeclContextForType(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType());
+ case clang::Type::Auto:
+ return GetDeclContextForType(
+ llvm::cast<clang::AutoType>(qual_type)->getDeducedType());
+ case clang::Type::Elaborated:
+ return GetDeclContextForType(
+ llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType());
+ case clang::Type::Paren:
+ return GetDeclContextForType(
+ llvm::cast<clang::ParenType>(qual_type)->desugar());
+ default:
+ break;
+ }
+ // No DeclContext in this type...
+ return nullptr;
+}
+
+static bool GetCompleteQualType(clang::ASTContext *ast,
+ clang::QualType qual_type,
+ bool allow_completion = true) {
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::ConstantArray:
+ case clang::Type::IncompleteArray:
+ case clang::Type::VariableArray: {
+ const clang::ArrayType *array_type =
+ llvm::dyn_cast<clang::ArrayType>(qual_type.getTypePtr());
+
+ if (array_type)
+ return GetCompleteQualType(ast, array_type->getElementType(),
+ allow_completion);
+ } break;
+ case clang::Type::Record: {
+ clang::CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
+ if (cxx_record_decl) {
+ if (cxx_record_decl->hasExternalLexicalStorage()) {
+ const bool is_complete = cxx_record_decl->isCompleteDefinition();
+ const bool fields_loaded =
+ cxx_record_decl->hasLoadedFieldsFromExternalStorage();
+ if (is_complete && fields_loaded)
+ return true;
+
+ if (!allow_completion)
+ return false;
+
+ // Call the field_begin() accessor to for it to use the external source
+ // to load the fields...
+ clang::ExternalASTSource *external_ast_source =
+ ast->getExternalSource();
+ if (external_ast_source) {
+ external_ast_source->CompleteType(cxx_record_decl);
+ if (cxx_record_decl->isCompleteDefinition()) {
+ cxx_record_decl->field_begin();
+ cxx_record_decl->setHasLoadedFieldsFromExternalStorage(true);
+ }
+ }
+ }
+ }
+ const clang::TagType *tag_type =
+ llvm::cast<clang::TagType>(qual_type.getTypePtr());
+ return !tag_type->isIncompleteType();
+ } break;
+
+ case clang::Type::Enum: {
+ const clang::TagType *tag_type =
+ llvm::dyn_cast<clang::TagType>(qual_type.getTypePtr());
+ if (tag_type) {
+ clang::TagDecl *tag_decl = tag_type->getDecl();
+ if (tag_decl) {
+ if (tag_decl->getDefinition())
+ return true;
+
+ if (!allow_completion)
+ return false;
+
+ if (tag_decl->hasExternalLexicalStorage()) {
+ if (ast) {
+ clang::ExternalASTSource *external_ast_source =
+ ast->getExternalSource();
+ if (external_ast_source) {
+ external_ast_source->CompleteType(tag_decl);
+ return !tag_type->isIncompleteType();
}
- break;
+ }
+ }
+ return false;
+ }
+ }
- case clang::Type::Enum:
- {
- const clang::TagType *tag_type = llvm::dyn_cast<clang::TagType>(qual_type.getTypePtr());
- if (tag_type)
- {
- clang::TagDecl *tag_decl = tag_type->getDecl();
- if (tag_decl)
- {
- if (tag_decl->getDefinition())
- return true;
-
- if (!allow_completion)
- return false;
-
- if (tag_decl->hasExternalLexicalStorage())
- {
- if (ast)
- {
- clang::ExternalASTSource *external_ast_source = ast->getExternalSource();
- if (external_ast_source)
- {
- external_ast_source->CompleteType(tag_decl);
- return !tag_type->isIncompleteType();
- }
- }
- }
- return false;
- }
- }
-
- }
- break;
- case clang::Type::ObjCObject:
- case clang::Type::ObjCInterface:
- {
- const clang::ObjCObjectType *objc_class_type = llvm::dyn_cast<clang::ObjCObjectType>(qual_type);
- if (objc_class_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
- // We currently can't complete objective C types through the newly added ASTContext
- // because it only supports TagDecl objects right now...
- if (class_interface_decl)
- {
- if (class_interface_decl->getDefinition())
- return true;
-
- if (!allow_completion)
- return false;
-
- if (class_interface_decl->hasExternalLexicalStorage())
- {
- if (ast)
- {
- clang::ExternalASTSource *external_ast_source = ast->getExternalSource();
- if (external_ast_source)
- {
- external_ast_source->CompleteType (class_interface_decl);
- return !objc_class_type->isIncompleteType();
- }
- }
- }
- return false;
- }
- }
+ } break;
+ case clang::Type::ObjCObject:
+ case clang::Type::ObjCInterface: {
+ const clang::ObjCObjectType *objc_class_type =
+ llvm::dyn_cast<clang::ObjCObjectType>(qual_type);
+ if (objc_class_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterface();
+ // We currently can't complete objective C types through the newly added
+ // ASTContext
+ // because it only supports TagDecl objects right now...
+ if (class_interface_decl) {
+ if (class_interface_decl->getDefinition())
+ return true;
+
+ if (!allow_completion)
+ return false;
+
+ if (class_interface_decl->hasExternalLexicalStorage()) {
+ if (ast) {
+ clang::ExternalASTSource *external_ast_source =
+ ast->getExternalSource();
+ if (external_ast_source) {
+ external_ast_source->CompleteType(class_interface_decl);
+ return !objc_class_type->isIncompleteType();
}
- break;
-
- case clang::Type::Typedef:
- return GetCompleteQualType (ast, llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType(), allow_completion);
-
- case clang::Type::Auto:
- return GetCompleteQualType (ast, llvm::cast<clang::AutoType>(qual_type)->getDeducedType(), allow_completion);
-
- case clang::Type::Elaborated:
- return GetCompleteQualType (ast, llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType(), allow_completion);
-
- case clang::Type::Paren:
- return GetCompleteQualType (ast, llvm::cast<clang::ParenType>(qual_type)->desugar(), allow_completion);
-
- case clang::Type::Attributed:
- return GetCompleteQualType (ast, llvm::cast<clang::AttributedType>(qual_type)->getModifiedType(), allow_completion);
-
- default:
- break;
+ }
+ }
+ return false;
+ }
}
-
- return true;
+ } break;
+
+ case clang::Type::Typedef:
+ return GetCompleteQualType(ast, llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType(),
+ allow_completion);
+
+ case clang::Type::Auto:
+ return GetCompleteQualType(
+ ast, llvm::cast<clang::AutoType>(qual_type)->getDeducedType(),
+ allow_completion);
+
+ case clang::Type::Elaborated:
+ return GetCompleteQualType(
+ ast, llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType(),
+ allow_completion);
+
+ case clang::Type::Paren:
+ return GetCompleteQualType(
+ ast, llvm::cast<clang::ParenType>(qual_type)->desugar(),
+ allow_completion);
+
+ case clang::Type::Attributed:
+ return GetCompleteQualType(
+ ast, llvm::cast<clang::AttributedType>(qual_type)->getModifiedType(),
+ allow_completion);
+
+ default:
+ break;
+ }
+
+ return true;
}
static clang::ObjCIvarDecl::AccessControl
-ConvertAccessTypeToObjCIvarAccessControl (AccessType access)
-{
- switch (access)
- {
- case eAccessNone: return clang::ObjCIvarDecl::None;
- case eAccessPublic: return clang::ObjCIvarDecl::Public;
- case eAccessPrivate: return clang::ObjCIvarDecl::Private;
- case eAccessProtected: return clang::ObjCIvarDecl::Protected;
- case eAccessPackage: return clang::ObjCIvarDecl::Package;
- }
+ConvertAccessTypeToObjCIvarAccessControl(AccessType access) {
+ switch (access) {
+ case eAccessNone:
return clang::ObjCIvarDecl::None;
+ case eAccessPublic:
+ return clang::ObjCIvarDecl::Public;
+ case eAccessPrivate:
+ return clang::ObjCIvarDecl::Private;
+ case eAccessProtected:
+ return clang::ObjCIvarDecl::Protected;
+ case eAccessPackage:
+ return clang::ObjCIvarDecl::Package;
+ }
+ return clang::ObjCIvarDecl::None;
}
-
//----------------------------------------------------------------------
// Tests
//----------------------------------------------------------------------
-bool
-ClangASTContext::IsAggregateType (lldb::opaque_compiler_type_t type)
-{
- clang::QualType qual_type (GetCanonicalQualType(type));
-
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::IncompleteArray:
- case clang::Type::VariableArray:
- case clang::Type::ConstantArray:
- case clang::Type::ExtVector:
- case clang::Type::Vector:
- case clang::Type::Record:
- case clang::Type::ObjCObject:
- case clang::Type::ObjCInterface:
- return true;
- case clang::Type::Auto:
- return IsAggregateType(llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr());
- case clang::Type::Elaborated:
- return IsAggregateType(llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr());
- case clang::Type::Typedef:
- return IsAggregateType(llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr());
- case clang::Type::Paren:
- return IsAggregateType(llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr());
- default:
- break;
- }
- // The clang type does have a value
- return false;
-}
-
-bool
-ClangASTContext::IsAnonymousType (lldb::opaque_compiler_type_t type)
-{
- clang::QualType qual_type (GetCanonicalQualType(type));
-
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Record:
- {
- if (const clang::RecordType *record_type = llvm::dyn_cast_or_null<clang::RecordType>(qual_type.getTypePtrOrNull()))
- {
- if (const clang::RecordDecl *record_decl = record_type->getDecl())
- {
- return record_decl->isAnonymousStructOrUnion();
- }
- }
- break;
- }
- case clang::Type::Auto:
- return IsAnonymousType(llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr());
- case clang::Type::Elaborated:
- return IsAnonymousType(llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr());
- case clang::Type::Typedef:
- return IsAnonymousType(llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr());
- case clang::Type::Paren:
- return IsAnonymousType(llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr());
- default:
- break;
- }
- // The clang type does have a value
- return false;
-}
-
-bool
-ClangASTContext::IsArrayType (lldb::opaque_compiler_type_t type,
- CompilerType *element_type_ptr,
- uint64_t *size,
- bool *is_incomplete)
-{
- clang::QualType qual_type (GetCanonicalQualType(type));
-
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- default:
- break;
-
- case clang::Type::ConstantArray:
- if (element_type_ptr)
- element_type_ptr->SetCompilerType (getASTContext(), llvm::cast<clang::ConstantArrayType>(qual_type)->getElementType());
- if (size)
- *size = llvm::cast<clang::ConstantArrayType>(qual_type)->getSize().getLimitedValue(ULLONG_MAX);
- if (is_incomplete)
- *is_incomplete = false;
- return true;
-
- case clang::Type::IncompleteArray:
- if (element_type_ptr)
- element_type_ptr->SetCompilerType (getASTContext(), llvm::cast<clang::IncompleteArrayType>(qual_type)->getElementType());
- if (size)
- *size = 0;
- if (is_incomplete)
- *is_incomplete = true;
- return true;
+bool ClangASTContext::IsAggregateType(lldb::opaque_compiler_type_t type) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::IncompleteArray:
+ case clang::Type::VariableArray:
+ case clang::Type::ConstantArray:
+ case clang::Type::ExtVector:
+ case clang::Type::Vector:
+ case clang::Type::Record:
+ case clang::Type::ObjCObject:
+ case clang::Type::ObjCInterface:
+ return true;
+ case clang::Type::Auto:
+ return IsAggregateType(llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr());
+ case clang::Type::Elaborated:
+ return IsAggregateType(llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr());
+ case clang::Type::Typedef:
+ return IsAggregateType(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr());
+ case clang::Type::Paren:
+ return IsAggregateType(
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr());
+ default:
+ break;
+ }
+ // The clang type does have a value
+ return false;
+}
+
+bool ClangASTContext::IsAnonymousType(lldb::opaque_compiler_type_t type) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Record: {
+ if (const clang::RecordType *record_type =
+ llvm::dyn_cast_or_null<clang::RecordType>(
+ qual_type.getTypePtrOrNull())) {
+ if (const clang::RecordDecl *record_decl = record_type->getDecl()) {
+ return record_decl->isAnonymousStructOrUnion();
+ }
+ }
+ break;
+ }
+ case clang::Type::Auto:
+ return IsAnonymousType(llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr());
+ case clang::Type::Elaborated:
+ return IsAnonymousType(llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr());
+ case clang::Type::Typedef:
+ return IsAnonymousType(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr());
+ case clang::Type::Paren:
+ return IsAnonymousType(
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr());
+ default:
+ break;
+ }
+ // The clang type does have a value
+ return false;
+}
+
+bool ClangASTContext::IsArrayType(lldb::opaque_compiler_type_t type,
+ CompilerType *element_type_ptr,
+ uint64_t *size, bool *is_incomplete) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ default:
+ break;
+
+ case clang::Type::ConstantArray:
+ if (element_type_ptr)
+ element_type_ptr->SetCompilerType(
+ getASTContext(),
+ llvm::cast<clang::ConstantArrayType>(qual_type)->getElementType());
+ if (size)
+ *size = llvm::cast<clang::ConstantArrayType>(qual_type)
+ ->getSize()
+ .getLimitedValue(ULLONG_MAX);
+ if (is_incomplete)
+ *is_incomplete = false;
+ return true;
- case clang::Type::VariableArray:
- if (element_type_ptr)
- element_type_ptr->SetCompilerType (getASTContext(), llvm::cast<clang::VariableArrayType>(qual_type)->getElementType());
- if (size)
- *size = 0;
- if (is_incomplete)
- *is_incomplete = false;
- return true;
+ case clang::Type::IncompleteArray:
+ if (element_type_ptr)
+ element_type_ptr->SetCompilerType(
+ getASTContext(),
+ llvm::cast<clang::IncompleteArrayType>(qual_type)->getElementType());
+ if (size)
+ *size = 0;
+ if (is_incomplete)
+ *is_incomplete = true;
+ return true;
- case clang::Type::DependentSizedArray:
- if (element_type_ptr)
- element_type_ptr->SetCompilerType (getASTContext(), llvm::cast<clang::DependentSizedArrayType>(qual_type)->getElementType());
- if (size)
- *size = 0;
- if (is_incomplete)
- *is_incomplete = false;
- return true;
+ case clang::Type::VariableArray:
+ if (element_type_ptr)
+ element_type_ptr->SetCompilerType(
+ getASTContext(),
+ llvm::cast<clang::VariableArrayType>(qual_type)->getElementType());
+ if (size)
+ *size = 0;
+ if (is_incomplete)
+ *is_incomplete = false;
+ return true;
- case clang::Type::Typedef:
- return IsArrayType(llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(),
- element_type_ptr,
- size,
- is_incomplete);
- case clang::Type::Auto:
- return IsArrayType(llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr(),
- element_type_ptr,
- size,
- is_incomplete);
- case clang::Type::Elaborated:
- return IsArrayType(llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr(),
- element_type_ptr,
- size,
- is_incomplete);
- case clang::Type::Paren:
- return IsArrayType(llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(),
- element_type_ptr,
- size,
- is_incomplete);
- }
+ case clang::Type::DependentSizedArray:
if (element_type_ptr)
- element_type_ptr->Clear();
+ element_type_ptr->SetCompilerType(
+ getASTContext(), llvm::cast<clang::DependentSizedArrayType>(qual_type)
+ ->getElementType());
if (size)
- *size = 0;
+ *size = 0;
if (is_incomplete)
- *is_incomplete = false;
- return false;
-}
+ *is_incomplete = false;
+ return true;
-bool
-ClangASTContext::IsVectorType (lldb::opaque_compiler_type_t type,
- CompilerType *element_type,
- uint64_t *size)
-{
- clang::QualType qual_type (GetCanonicalQualType(type));
-
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Vector:
- {
- const clang::VectorType *vector_type = qual_type->getAs<clang::VectorType>();
- if (vector_type)
- {
- if (size)
- *size = vector_type->getNumElements();
- if (element_type)
- *element_type = CompilerType(getASTContext(), vector_type->getElementType());
- }
- return true;
- }
- break;
- case clang::Type::ExtVector:
- {
- const clang::ExtVectorType *ext_vector_type = qual_type->getAs<clang::ExtVectorType>();
- if (ext_vector_type)
- {
- if (size)
- *size = ext_vector_type->getNumElements();
- if (element_type)
- *element_type = CompilerType(getASTContext(), ext_vector_type->getElementType());
- }
- return true;
- }
- default:
- break;
+ case clang::Type::Typedef:
+ return IsArrayType(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr(),
+ element_type_ptr, size, is_incomplete);
+ case clang::Type::Auto:
+ return IsArrayType(llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr(),
+ element_type_ptr, size, is_incomplete);
+ case clang::Type::Elaborated:
+ return IsArrayType(llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr(),
+ element_type_ptr, size, is_incomplete);
+ case clang::Type::Paren:
+ return IsArrayType(
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(),
+ element_type_ptr, size, is_incomplete);
+ }
+ if (element_type_ptr)
+ element_type_ptr->Clear();
+ if (size)
+ *size = 0;
+ if (is_incomplete)
+ *is_incomplete = false;
+ return false;
+}
+
+bool ClangASTContext::IsVectorType(lldb::opaque_compiler_type_t type,
+ CompilerType *element_type, uint64_t *size) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Vector: {
+ const clang::VectorType *vector_type =
+ qual_type->getAs<clang::VectorType>();
+ if (vector_type) {
+ if (size)
+ *size = vector_type->getNumElements();
+ if (element_type)
+ *element_type =
+ CompilerType(getASTContext(), vector_type->getElementType());
}
+ return true;
+ } break;
+ case clang::Type::ExtVector: {
+ const clang::ExtVectorType *ext_vector_type =
+ qual_type->getAs<clang::ExtVectorType>();
+ if (ext_vector_type) {
+ if (size)
+ *size = ext_vector_type->getNumElements();
+ if (element_type)
+ *element_type =
+ CompilerType(getASTContext(), ext_vector_type->getElementType());
+ }
+ return true;
+ }
+ default:
+ break;
+ }
+ return false;
+}
+
+bool ClangASTContext::IsRuntimeGeneratedType(
+ lldb::opaque_compiler_type_t type) {
+ clang::DeclContext *decl_ctx = ClangASTContext::GetASTContext(getASTContext())
+ ->GetDeclContextForType(GetQualType(type));
+ if (!decl_ctx)
return false;
-}
-bool
-ClangASTContext::IsRuntimeGeneratedType (lldb::opaque_compiler_type_t type)
-{
- clang::DeclContext* decl_ctx = ClangASTContext::GetASTContext(getASTContext())->GetDeclContextForType(GetQualType(type));
- if (!decl_ctx)
- return false;
-
- if (!llvm::isa<clang::ObjCInterfaceDecl>(decl_ctx))
- return false;
-
- clang::ObjCInterfaceDecl *result_iface_decl = llvm::dyn_cast<clang::ObjCInterfaceDecl>(decl_ctx);
-
- ClangASTMetadata* ast_metadata = ClangASTContext::GetMetadata(getASTContext(), result_iface_decl);
- if (!ast_metadata)
- return false;
- return (ast_metadata->GetISAPtr() != 0);
-}
+ if (!llvm::isa<clang::ObjCInterfaceDecl>(decl_ctx))
+ return false;
+
+ clang::ObjCInterfaceDecl *result_iface_decl =
+ llvm::dyn_cast<clang::ObjCInterfaceDecl>(decl_ctx);
-bool
-ClangASTContext::IsCharType (lldb::opaque_compiler_type_t type)
-{
- return GetQualType(type).getUnqualifiedType()->isCharType();
+ ClangASTMetadata *ast_metadata =
+ ClangASTContext::GetMetadata(getASTContext(), result_iface_decl);
+ if (!ast_metadata)
+ return false;
+ return (ast_metadata->GetISAPtr() != 0);
}
+bool ClangASTContext::IsCharType(lldb::opaque_compiler_type_t type) {
+ return GetQualType(type).getUnqualifiedType()->isCharType();
+}
-bool
-ClangASTContext::IsCompleteType (lldb::opaque_compiler_type_t type)
-{
- const bool allow_completion = false;
- return GetCompleteQualType (getASTContext(), GetQualType(type), allow_completion);
+bool ClangASTContext::IsCompleteType(lldb::opaque_compiler_type_t type) {
+ const bool allow_completion = false;
+ return GetCompleteQualType(getASTContext(), GetQualType(type),
+ allow_completion);
}
-bool
-ClangASTContext::IsConst(lldb::opaque_compiler_type_t type)
-{
- return GetQualType(type).isConstQualified();
+bool ClangASTContext::IsConst(lldb::opaque_compiler_type_t type) {
+ return GetQualType(type).isConstQualified();
}
-bool
-ClangASTContext::IsCStringType (lldb::opaque_compiler_type_t type, uint32_t &length)
-{
- CompilerType pointee_or_element_clang_type;
- length = 0;
- Flags type_flags (GetTypeInfo (type, &pointee_or_element_clang_type));
-
- if (!pointee_or_element_clang_type.IsValid())
- return false;
-
- if (type_flags.AnySet (eTypeIsArray | eTypeIsPointer))
- {
- if (pointee_or_element_clang_type.IsCharType())
- {
- if (type_flags.Test (eTypeIsArray))
- {
- // We know the size of the array and it could be a C string
- // since it is an array of characters
- length = llvm::cast<clang::ConstantArrayType>(GetCanonicalQualType(type).getTypePtr())->getSize().getLimitedValue();
- }
- return true;
-
- }
- }
+bool ClangASTContext::IsCStringType(lldb::opaque_compiler_type_t type,
+ uint32_t &length) {
+ CompilerType pointee_or_element_clang_type;
+ length = 0;
+ Flags type_flags(GetTypeInfo(type, &pointee_or_element_clang_type));
+
+ if (!pointee_or_element_clang_type.IsValid())
return false;
-}
-bool
-ClangASTContext::IsFunctionType (lldb::opaque_compiler_type_t type, bool *is_variadic_ptr)
-{
- if (type)
- {
- clang::QualType qual_type (GetCanonicalQualType(type));
-
- if (qual_type->isFunctionType())
- {
- if (is_variadic_ptr)
- {
- const clang::FunctionProtoType *function_proto_type = llvm::dyn_cast<clang::FunctionProtoType>(qual_type.getTypePtr());
- if (function_proto_type)
- *is_variadic_ptr = function_proto_type->isVariadic();
- else
- *is_variadic_ptr = false;
- }
- return true;
- }
-
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- default:
- break;
- case clang::Type::Typedef:
- return IsFunctionType(llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(), nullptr);
- case clang::Type::Auto:
- return IsFunctionType(llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr(), nullptr);
- case clang::Type::Elaborated:
- return IsFunctionType(llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr(), nullptr);
- case clang::Type::Paren:
- return IsFunctionType(llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(), nullptr);
- case clang::Type::LValueReference:
- case clang::Type::RValueReference:
- {
- const clang::ReferenceType *reference_type = llvm::cast<clang::ReferenceType>(qual_type.getTypePtr());
- if (reference_type)
- return IsFunctionType(reference_type->getPointeeType().getAsOpaquePtr(), nullptr);
- }
- break;
- }
+ if (type_flags.AnySet(eTypeIsArray | eTypeIsPointer)) {
+ if (pointee_or_element_clang_type.IsCharType()) {
+ if (type_flags.Test(eTypeIsArray)) {
+ // We know the size of the array and it could be a C string
+ // since it is an array of characters
+ length = llvm::cast<clang::ConstantArrayType>(
+ GetCanonicalQualType(type).getTypePtr())
+ ->getSize()
+ .getLimitedValue();
+ }
+ return true;
+ }
+ }
+ return false;
+}
+
+bool ClangASTContext::IsFunctionType(lldb::opaque_compiler_type_t type,
+ bool *is_variadic_ptr) {
+ if (type) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+
+ if (qual_type->isFunctionType()) {
+ if (is_variadic_ptr) {
+ const clang::FunctionProtoType *function_proto_type =
+ llvm::dyn_cast<clang::FunctionProtoType>(qual_type.getTypePtr());
+ if (function_proto_type)
+ *is_variadic_ptr = function_proto_type->isVariadic();
+ else
+ *is_variadic_ptr = false;
+ }
+ return true;
}
- return false;
+
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ default:
+ break;
+ case clang::Type::Typedef:
+ return IsFunctionType(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr(),
+ nullptr);
+ case clang::Type::Auto:
+ return IsFunctionType(llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr(),
+ nullptr);
+ case clang::Type::Elaborated:
+ return IsFunctionType(llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr(),
+ nullptr);
+ case clang::Type::Paren:
+ return IsFunctionType(
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(),
+ nullptr);
+ case clang::Type::LValueReference:
+ case clang::Type::RValueReference: {
+ const clang::ReferenceType *reference_type =
+ llvm::cast<clang::ReferenceType>(qual_type.getTypePtr());
+ if (reference_type)
+ return IsFunctionType(reference_type->getPointeeType().getAsOpaquePtr(),
+ nullptr);
+ } break;
+ }
+ }
+ return false;
}
// Used to detect "Homogeneous Floating-point Aggregates"
uint32_t
-ClangASTContext::IsHomogeneousAggregate (lldb::opaque_compiler_type_t type, CompilerType* base_type_ptr)
-{
- if (!type)
- return 0;
-
- clang::QualType qual_type(GetCanonicalQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Record:
- if (GetCompleteType (type))
- {
- const clang::CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
- if (cxx_record_decl)
- {
- if (cxx_record_decl->getNumBases() ||
- cxx_record_decl->isDynamicClass())
- return 0;
- }
- const clang::RecordType *record_type = llvm::cast<clang::RecordType>(qual_type.getTypePtr());
- if (record_type)
- {
- const clang::RecordDecl *record_decl = record_type->getDecl();
- if (record_decl)
- {
- // We are looking for a structure that contains only floating point types
- clang::RecordDecl::field_iterator field_pos, field_end = record_decl->field_end();
- uint32_t num_fields = 0;
- bool is_hva = false;
- bool is_hfa = false;
- clang::QualType base_qual_type;
- uint64_t base_bitwidth = 0;
- for (field_pos = record_decl->field_begin(); field_pos != field_end; ++field_pos)
- {
- clang::QualType field_qual_type = field_pos->getType();
- uint64_t field_bitwidth = getASTContext()->getTypeSize (qual_type);
- if (field_qual_type->isFloatingType())
- {
- if (field_qual_type->isComplexType())
- return 0;
- else
- {
- if (num_fields == 0)
- base_qual_type = field_qual_type;
- else
- {
- if (is_hva)
- return 0;
- is_hfa = true;
- if (field_qual_type.getTypePtr() != base_qual_type.getTypePtr())
- return 0;
- }
- }
- }
- else if (field_qual_type->isVectorType() || field_qual_type->isExtVectorType())
- {
- if (num_fields == 0)
- {
- base_qual_type = field_qual_type;
- base_bitwidth = field_bitwidth;
- }
- else
- {
- if (is_hfa)
- return 0;
- is_hva = true;
- if (base_bitwidth != field_bitwidth)
- return 0;
- if (field_qual_type.getTypePtr() != base_qual_type.getTypePtr())
- return 0;
- }
- }
- else
- return 0;
- ++num_fields;
- }
- if (base_type_ptr)
- *base_type_ptr = CompilerType (getASTContext(), base_qual_type);
- return num_fields;
- }
- }
- }
- break;
-
- case clang::Type::Typedef:
- return IsHomogeneousAggregate(llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(), base_type_ptr);
-
- case clang::Type::Auto:
- return IsHomogeneousAggregate(llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr(), base_type_ptr);
-
- case clang::Type::Elaborated:
- return IsHomogeneousAggregate(llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr(), base_type_ptr);
- default:
- break;
- }
+ClangASTContext::IsHomogeneousAggregate(lldb::opaque_compiler_type_t type,
+ CompilerType *base_type_ptr) {
+ if (!type)
return 0;
-}
-size_t
-ClangASTContext::GetNumberOfFunctionArguments (lldb::opaque_compiler_type_t type)
-{
- if (type)
- {
- clang::QualType qual_type (GetCanonicalQualType(type));
- const clang::FunctionProtoType* func = llvm::dyn_cast<clang::FunctionProtoType>(qual_type.getTypePtr());
- if (func)
- return func->getNumParams();
- }
- return 0;
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Record:
+ if (GetCompleteType(type)) {
+ const clang::CXXRecordDecl *cxx_record_decl =
+ qual_type->getAsCXXRecordDecl();
+ if (cxx_record_decl) {
+ if (cxx_record_decl->getNumBases() || cxx_record_decl->isDynamicClass())
+ return 0;
+ }
+ const clang::RecordType *record_type =
+ llvm::cast<clang::RecordType>(qual_type.getTypePtr());
+ if (record_type) {
+ const clang::RecordDecl *record_decl = record_type->getDecl();
+ if (record_decl) {
+ // We are looking for a structure that contains only floating point
+ // types
+ clang::RecordDecl::field_iterator field_pos,
+ field_end = record_decl->field_end();
+ uint32_t num_fields = 0;
+ bool is_hva = false;
+ bool is_hfa = false;
+ clang::QualType base_qual_type;
+ uint64_t base_bitwidth = 0;
+ for (field_pos = record_decl->field_begin(); field_pos != field_end;
+ ++field_pos) {
+ clang::QualType field_qual_type = field_pos->getType();
+ uint64_t field_bitwidth = getASTContext()->getTypeSize(qual_type);
+ if (field_qual_type->isFloatingType()) {
+ if (field_qual_type->isComplexType())
+ return 0;
+ else {
+ if (num_fields == 0)
+ base_qual_type = field_qual_type;
+ else {
+ if (is_hva)
+ return 0;
+ is_hfa = true;
+ if (field_qual_type.getTypePtr() !=
+ base_qual_type.getTypePtr())
+ return 0;
+ }
+ }
+ } else if (field_qual_type->isVectorType() ||
+ field_qual_type->isExtVectorType()) {
+ if (num_fields == 0) {
+ base_qual_type = field_qual_type;
+ base_bitwidth = field_bitwidth;
+ } else {
+ if (is_hfa)
+ return 0;
+ is_hva = true;
+ if (base_bitwidth != field_bitwidth)
+ return 0;
+ if (field_qual_type.getTypePtr() != base_qual_type.getTypePtr())
+ return 0;
+ }
+ } else
+ return 0;
+ ++num_fields;
+ }
+ if (base_type_ptr)
+ *base_type_ptr = CompilerType(getASTContext(), base_qual_type);
+ return num_fields;
+ }
+ }
+ }
+ break;
+
+ case clang::Type::Typedef:
+ return IsHomogeneousAggregate(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr(),
+ base_type_ptr);
+
+ case clang::Type::Auto:
+ return IsHomogeneousAggregate(llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr(),
+ base_type_ptr);
+
+ case clang::Type::Elaborated:
+ return IsHomogeneousAggregate(llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr(),
+ base_type_ptr);
+ default:
+ break;
+ }
+ return 0;
+}
+
+size_t ClangASTContext::GetNumberOfFunctionArguments(
+ lldb::opaque_compiler_type_t type) {
+ if (type) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::FunctionProtoType *func =
+ llvm::dyn_cast<clang::FunctionProtoType>(qual_type.getTypePtr());
+ if (func)
+ return func->getNumParams();
+ }
+ return 0;
}
CompilerType
-ClangASTContext::GetFunctionArgumentAtIndex (lldb::opaque_compiler_type_t type, const size_t index)
-{
- if (type)
- {
- clang::QualType qual_type (GetQualType(type));
- const clang::FunctionProtoType* func = llvm::dyn_cast<clang::FunctionProtoType>(qual_type.getTypePtr());
- if (func)
- {
- if (index < func->getNumParams())
- return CompilerType(getASTContext(), func->getParamType(index));
- }
+ClangASTContext::GetFunctionArgumentAtIndex(lldb::opaque_compiler_type_t type,
+ const size_t index) {
+ if (type) {
+ clang::QualType qual_type(GetQualType(type));
+ const clang::FunctionProtoType *func =
+ llvm::dyn_cast<clang::FunctionProtoType>(qual_type.getTypePtr());
+ if (func) {
+ if (index < func->getNumParams())
+ return CompilerType(getASTContext(), func->getParamType(index));
}
- return CompilerType();
+ }
+ return CompilerType();
}
-bool
-ClangASTContext::IsFunctionPointerType (lldb::opaque_compiler_type_t type)
-{
- if (type)
- {
- clang::QualType qual_type (GetCanonicalQualType(type));
-
- if (qual_type->isFunctionPointerType())
- return true;
-
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- default:
- break;
- case clang::Type::Typedef:
- return IsFunctionPointerType (llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr());
- case clang::Type::Auto:
- return IsFunctionPointerType (llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr());
- case clang::Type::Elaborated:
- return IsFunctionPointerType (llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr());
- case clang::Type::Paren:
- return IsFunctionPointerType (llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr());
-
- case clang::Type::LValueReference:
- case clang::Type::RValueReference:
- {
- const clang::ReferenceType *reference_type = llvm::cast<clang::ReferenceType>(qual_type.getTypePtr());
- if (reference_type)
- return IsFunctionPointerType(reference_type->getPointeeType().getAsOpaquePtr());
- }
- break;
- }
- }
- return false;
-
-}
-
-bool
-ClangASTContext::IsBlockPointerType (lldb::opaque_compiler_type_t type, CompilerType *function_pointer_type_ptr)
-{
- if (type)
- {
- clang::QualType qual_type (GetCanonicalQualType(type));
-
- if (qual_type->isBlockPointerType())
- {
- if (function_pointer_type_ptr)
- {
- const clang::BlockPointerType *block_pointer_type = qual_type->getAs<clang::BlockPointerType>();
- QualType pointee_type = block_pointer_type->getPointeeType();
- QualType function_pointer_type = m_ast_ap->getPointerType(pointee_type);
- *function_pointer_type_ptr = CompilerType (getASTContext(), function_pointer_type);
- }
- return true;
- }
-
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- default:
- break;
- case clang::Type::Typedef:
- return IsBlockPointerType (llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(), function_pointer_type_ptr);
- case clang::Type::Auto:
- return IsBlockPointerType (llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr(), function_pointer_type_ptr);
- case clang::Type::Elaborated:
- return IsBlockPointerType (llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr(), function_pointer_type_ptr);
- case clang::Type::Paren:
- return IsBlockPointerType (llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(), function_pointer_type_ptr);
-
- case clang::Type::LValueReference:
- case clang::Type::RValueReference:
- {
- const clang::ReferenceType *reference_type = llvm::cast<clang::ReferenceType>(qual_type.getTypePtr());
- if (reference_type)
- return IsBlockPointerType(reference_type->getPointeeType().getAsOpaquePtr(), function_pointer_type_ptr);
- }
- break;
- }
+bool ClangASTContext::IsFunctionPointerType(lldb::opaque_compiler_type_t type) {
+ if (type) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+
+ if (qual_type->isFunctionPointerType())
+ return true;
+
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ default:
+ break;
+ case clang::Type::Typedef:
+ return IsFunctionPointerType(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr());
+ case clang::Type::Auto:
+ return IsFunctionPointerType(llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr());
+ case clang::Type::Elaborated:
+ return IsFunctionPointerType(llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr());
+ case clang::Type::Paren:
+ return IsFunctionPointerType(
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr());
+
+ case clang::Type::LValueReference:
+ case clang::Type::RValueReference: {
+ const clang::ReferenceType *reference_type =
+ llvm::cast<clang::ReferenceType>(qual_type.getTypePtr());
+ if (reference_type)
+ return IsFunctionPointerType(
+ reference_type->getPointeeType().getAsOpaquePtr());
+ } break;
+ }
+ }
+ return false;
+}
+
+bool ClangASTContext::IsBlockPointerType(
+ lldb::opaque_compiler_type_t type,
+ CompilerType *function_pointer_type_ptr) {
+ if (type) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+
+ if (qual_type->isBlockPointerType()) {
+ if (function_pointer_type_ptr) {
+ const clang::BlockPointerType *block_pointer_type =
+ qual_type->getAs<clang::BlockPointerType>();
+ QualType pointee_type = block_pointer_type->getPointeeType();
+ QualType function_pointer_type = m_ast_ap->getPointerType(pointee_type);
+ *function_pointer_type_ptr =
+ CompilerType(getASTContext(), function_pointer_type);
+ }
+ return true;
}
+
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ default:
+ break;
+ case clang::Type::Typedef:
+ return IsBlockPointerType(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr(),
+ function_pointer_type_ptr);
+ case clang::Type::Auto:
+ return IsBlockPointerType(llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr(),
+ function_pointer_type_ptr);
+ case clang::Type::Elaborated:
+ return IsBlockPointerType(llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr(),
+ function_pointer_type_ptr);
+ case clang::Type::Paren:
+ return IsBlockPointerType(
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(),
+ function_pointer_type_ptr);
+
+ case clang::Type::LValueReference:
+ case clang::Type::RValueReference: {
+ const clang::ReferenceType *reference_type =
+ llvm::cast<clang::ReferenceType>(qual_type.getTypePtr());
+ if (reference_type)
+ return IsBlockPointerType(
+ reference_type->getPointeeType().getAsOpaquePtr(),
+ function_pointer_type_ptr);
+ } break;
+ }
+ }
+ return false;
+}
+
+bool ClangASTContext::IsIntegerType(lldb::opaque_compiler_type_t type,
+ bool &is_signed) {
+ if (!type)
return false;
-}
-bool
-ClangASTContext::IsIntegerType (lldb::opaque_compiler_type_t type, bool &is_signed)
-{
- if (!type)
- return false;
-
- clang::QualType qual_type (GetCanonicalQualType(type));
- const clang::BuiltinType *builtin_type = llvm::dyn_cast<clang::BuiltinType>(qual_type->getCanonicalTypeInternal());
-
- if (builtin_type)
- {
- if (builtin_type->isInteger())
- {
- is_signed = builtin_type->isSignedInteger();
- return true;
- }
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::BuiltinType *builtin_type =
+ llvm::dyn_cast<clang::BuiltinType>(qual_type->getCanonicalTypeInternal());
+
+ if (builtin_type) {
+ if (builtin_type->isInteger()) {
+ is_signed = builtin_type->isSignedInteger();
+ return true;
}
-
- return false;
+ }
+
+ return false;
}
-bool
-ClangASTContext::IsEnumerationType(lldb::opaque_compiler_type_t type, bool &is_signed)
-{
- if (type)
- {
- const clang::EnumType *enum_type = llvm::dyn_cast<clang::EnumType>(GetCanonicalQualType(type)->getCanonicalTypeInternal());
+bool ClangASTContext::IsEnumerationType(lldb::opaque_compiler_type_t type,
+ bool &is_signed) {
+ if (type) {
+ const clang::EnumType *enum_type = llvm::dyn_cast<clang::EnumType>(
+ GetCanonicalQualType(type)->getCanonicalTypeInternal());
- if (enum_type)
- {
- IsIntegerType(enum_type->getDecl()->getIntegerType().getAsOpaquePtr(), is_signed);
- return true;
- }
+ if (enum_type) {
+ IsIntegerType(enum_type->getDecl()->getIntegerType().getAsOpaquePtr(),
+ is_signed);
+ return true;
}
+ }
- return false;
+ return false;
}
-bool
-ClangASTContext::IsPointerType (lldb::opaque_compiler_type_t type, CompilerType *pointee_type)
-{
- if (type)
- {
- clang::QualType qual_type (GetCanonicalQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Builtin:
- switch (llvm::cast<clang::BuiltinType>(qual_type)->getKind())
- {
- default:
- break;
- case clang::BuiltinType::ObjCId:
- case clang::BuiltinType::ObjCClass:
- return true;
- }
- return false;
- case clang::Type::ObjCObjectPointer:
- if (pointee_type)
- pointee_type->SetCompilerType (getASTContext(), llvm::cast<clang::ObjCObjectPointerType>(qual_type)->getPointeeType());
- return true;
- case clang::Type::BlockPointer:
- if (pointee_type)
- pointee_type->SetCompilerType (getASTContext(), llvm::cast<clang::BlockPointerType>(qual_type)->getPointeeType());
- return true;
- case clang::Type::Pointer:
- if (pointee_type)
- pointee_type->SetCompilerType (getASTContext(), llvm::cast<clang::PointerType>(qual_type)->getPointeeType());
- return true;
- case clang::Type::MemberPointer:
- if (pointee_type)
- pointee_type->SetCompilerType (getASTContext(), llvm::cast<clang::MemberPointerType>(qual_type)->getPointeeType());
- return true;
- case clang::Type::Typedef:
- return IsPointerType (llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(), pointee_type);
- case clang::Type::Auto:
- return IsPointerType (llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr(), pointee_type);
- case clang::Type::Elaborated:
- return IsPointerType (llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr(), pointee_type);
- case clang::Type::Paren:
- return IsPointerType (llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(), pointee_type);
- default:
- break;
- }
+bool ClangASTContext::IsPointerType(lldb::opaque_compiler_type_t type,
+ CompilerType *pointee_type) {
+ if (type) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Builtin:
+ switch (llvm::cast<clang::BuiltinType>(qual_type)->getKind()) {
+ default:
+ break;
+ case clang::BuiltinType::ObjCId:
+ case clang::BuiltinType::ObjCClass:
+ return true;
+ }
+ return false;
+ case clang::Type::ObjCObjectPointer:
+ if (pointee_type)
+ pointee_type->SetCompilerType(
+ getASTContext(), llvm::cast<clang::ObjCObjectPointerType>(qual_type)
+ ->getPointeeType());
+ return true;
+ case clang::Type::BlockPointer:
+ if (pointee_type)
+ pointee_type->SetCompilerType(
+ getASTContext(),
+ llvm::cast<clang::BlockPointerType>(qual_type)->getPointeeType());
+ return true;
+ case clang::Type::Pointer:
+ if (pointee_type)
+ pointee_type->SetCompilerType(
+ getASTContext(),
+ llvm::cast<clang::PointerType>(qual_type)->getPointeeType());
+ return true;
+ case clang::Type::MemberPointer:
+ if (pointee_type)
+ pointee_type->SetCompilerType(
+ getASTContext(),
+ llvm::cast<clang::MemberPointerType>(qual_type)->getPointeeType());
+ return true;
+ case clang::Type::Typedef:
+ return IsPointerType(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr(),
+ pointee_type);
+ case clang::Type::Auto:
+ return IsPointerType(llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr(),
+ pointee_type);
+ case clang::Type::Elaborated:
+ return IsPointerType(llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr(),
+ pointee_type);
+ case clang::Type::Paren:
+ return IsPointerType(
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(),
+ pointee_type);
+ default:
+ break;
}
- if (pointee_type)
- pointee_type->Clear();
- return false;
+ }
+ if (pointee_type)
+ pointee_type->Clear();
+ return false;
}
-
-bool
-ClangASTContext::IsPointerOrReferenceType (lldb::opaque_compiler_type_t type, CompilerType *pointee_type)
-{
- if (type)
- {
- clang::QualType qual_type (GetCanonicalQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Builtin:
- switch (llvm::cast<clang::BuiltinType>(qual_type)->getKind())
- {
- default:
- break;
- case clang::BuiltinType::ObjCId:
- case clang::BuiltinType::ObjCClass:
- return true;
- }
- return false;
- case clang::Type::ObjCObjectPointer:
- if (pointee_type)
- pointee_type->SetCompilerType(getASTContext(), llvm::cast<clang::ObjCObjectPointerType>(qual_type)->getPointeeType());
- return true;
- case clang::Type::BlockPointer:
- if (pointee_type)
- pointee_type->SetCompilerType(getASTContext(), llvm::cast<clang::BlockPointerType>(qual_type)->getPointeeType());
- return true;
- case clang::Type::Pointer:
- if (pointee_type)
- pointee_type->SetCompilerType(getASTContext(), llvm::cast<clang::PointerType>(qual_type)->getPointeeType());
- return true;
- case clang::Type::MemberPointer:
- if (pointee_type)
- pointee_type->SetCompilerType(getASTContext(), llvm::cast<clang::MemberPointerType>(qual_type)->getPointeeType());
- return true;
- case clang::Type::LValueReference:
- if (pointee_type)
- pointee_type->SetCompilerType(getASTContext(), llvm::cast<clang::LValueReferenceType>(qual_type)->desugar());
- return true;
- case clang::Type::RValueReference:
- if (pointee_type)
- pointee_type->SetCompilerType(getASTContext(), llvm::cast<clang::RValueReferenceType>(qual_type)->desugar());
- return true;
- case clang::Type::Typedef:
- return IsPointerOrReferenceType(llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(), pointee_type);
- case clang::Type::Auto:
- return IsPointerOrReferenceType(llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr(), pointee_type);
- case clang::Type::Elaborated:
- return IsPointerOrReferenceType(llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr(), pointee_type);
- case clang::Type::Paren:
- return IsPointerOrReferenceType(llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(), pointee_type);
- default:
- break;
- }
+bool ClangASTContext::IsPointerOrReferenceType(
+ lldb::opaque_compiler_type_t type, CompilerType *pointee_type) {
+ if (type) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Builtin:
+ switch (llvm::cast<clang::BuiltinType>(qual_type)->getKind()) {
+ default:
+ break;
+ case clang::BuiltinType::ObjCId:
+ case clang::BuiltinType::ObjCClass:
+ return true;
+ }
+ return false;
+ case clang::Type::ObjCObjectPointer:
+ if (pointee_type)
+ pointee_type->SetCompilerType(
+ getASTContext(), llvm::cast<clang::ObjCObjectPointerType>(qual_type)
+ ->getPointeeType());
+ return true;
+ case clang::Type::BlockPointer:
+ if (pointee_type)
+ pointee_type->SetCompilerType(
+ getASTContext(),
+ llvm::cast<clang::BlockPointerType>(qual_type)->getPointeeType());
+ return true;
+ case clang::Type::Pointer:
+ if (pointee_type)
+ pointee_type->SetCompilerType(
+ getASTContext(),
+ llvm::cast<clang::PointerType>(qual_type)->getPointeeType());
+ return true;
+ case clang::Type::MemberPointer:
+ if (pointee_type)
+ pointee_type->SetCompilerType(
+ getASTContext(),
+ llvm::cast<clang::MemberPointerType>(qual_type)->getPointeeType());
+ return true;
+ case clang::Type::LValueReference:
+ if (pointee_type)
+ pointee_type->SetCompilerType(
+ getASTContext(),
+ llvm::cast<clang::LValueReferenceType>(qual_type)->desugar());
+ return true;
+ case clang::Type::RValueReference:
+ if (pointee_type)
+ pointee_type->SetCompilerType(
+ getASTContext(),
+ llvm::cast<clang::RValueReferenceType>(qual_type)->desugar());
+ return true;
+ case clang::Type::Typedef:
+ return IsPointerOrReferenceType(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr(),
+ pointee_type);
+ case clang::Type::Auto:
+ return IsPointerOrReferenceType(llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr(),
+ pointee_type);
+ case clang::Type::Elaborated:
+ return IsPointerOrReferenceType(
+ llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr(),
+ pointee_type);
+ case clang::Type::Paren:
+ return IsPointerOrReferenceType(
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(),
+ pointee_type);
+ default:
+ break;
}
- if (pointee_type)
- pointee_type->Clear();
- return false;
+ }
+ if (pointee_type)
+ pointee_type->Clear();
+ return false;
}
+bool ClangASTContext::IsReferenceType(lldb::opaque_compiler_type_t type,
+ CompilerType *pointee_type,
+ bool *is_rvalue) {
+ if (type) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
-bool
-ClangASTContext::IsReferenceType (lldb::opaque_compiler_type_t type, CompilerType *pointee_type, bool* is_rvalue)
-{
- if (type)
- {
- clang::QualType qual_type (GetCanonicalQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
-
- switch (type_class)
- {
- case clang::Type::LValueReference:
- if (pointee_type)
- pointee_type->SetCompilerType(getASTContext(), llvm::cast<clang::LValueReferenceType>(qual_type)->desugar());
- if (is_rvalue)
- *is_rvalue = false;
- return true;
- case clang::Type::RValueReference:
- if (pointee_type)
- pointee_type->SetCompilerType(getASTContext(), llvm::cast<clang::RValueReferenceType>(qual_type)->desugar());
- if (is_rvalue)
- *is_rvalue = true;
- return true;
- case clang::Type::Typedef:
- return IsReferenceType (llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(), pointee_type, is_rvalue);
- case clang::Type::Auto:
- return IsReferenceType (llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr(), pointee_type, is_rvalue);
- case clang::Type::Elaborated:
- return IsReferenceType (llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr(), pointee_type, is_rvalue);
- case clang::Type::Paren:
- return IsReferenceType (llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(), pointee_type, is_rvalue);
-
- default:
- break;
- }
+ switch (type_class) {
+ case clang::Type::LValueReference:
+ if (pointee_type)
+ pointee_type->SetCompilerType(
+ getASTContext(),
+ llvm::cast<clang::LValueReferenceType>(qual_type)->desugar());
+ if (is_rvalue)
+ *is_rvalue = false;
+ return true;
+ case clang::Type::RValueReference:
+ if (pointee_type)
+ pointee_type->SetCompilerType(
+ getASTContext(),
+ llvm::cast<clang::RValueReferenceType>(qual_type)->desugar());
+ if (is_rvalue)
+ *is_rvalue = true;
+ return true;
+ case clang::Type::Typedef:
+ return IsReferenceType(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr(),
+ pointee_type, is_rvalue);
+ case clang::Type::Auto:
+ return IsReferenceType(llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr(),
+ pointee_type, is_rvalue);
+ case clang::Type::Elaborated:
+ return IsReferenceType(llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr(),
+ pointee_type, is_rvalue);
+ case clang::Type::Paren:
+ return IsReferenceType(
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(),
+ pointee_type, is_rvalue);
+
+ default:
+ break;
}
- if (pointee_type)
- pointee_type->Clear();
- return false;
+ }
+ if (pointee_type)
+ pointee_type->Clear();
+ return false;
}
-bool
-ClangASTContext::IsFloatingPointType (lldb::opaque_compiler_type_t type, uint32_t &count, bool &is_complex)
-{
- if (type)
- {
- clang::QualType qual_type (GetCanonicalQualType(type));
-
- if (const clang::BuiltinType *BT = llvm::dyn_cast<clang::BuiltinType>(qual_type->getCanonicalTypeInternal()))
- {
- clang::BuiltinType::Kind kind = BT->getKind();
- if (kind >= clang::BuiltinType::Float && kind <= clang::BuiltinType::LongDouble)
- {
- count = 1;
- is_complex = false;
- return true;
- }
- }
- else if (const clang::ComplexType *CT = llvm::dyn_cast<clang::ComplexType>(qual_type->getCanonicalTypeInternal()))
- {
- if (IsFloatingPointType (CT->getElementType().getAsOpaquePtr(), count, is_complex))
- {
- count = 2;
- is_complex = true;
- return true;
- }
- }
- else if (const clang::VectorType *VT = llvm::dyn_cast<clang::VectorType>(qual_type->getCanonicalTypeInternal()))
- {
- if (IsFloatingPointType (VT->getElementType().getAsOpaquePtr(), count, is_complex))
- {
- count = VT->getNumElements();
- is_complex = false;
- return true;
- }
- }
+bool ClangASTContext::IsFloatingPointType(lldb::opaque_compiler_type_t type,
+ uint32_t &count, bool &is_complex) {
+ if (type) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+
+ if (const clang::BuiltinType *BT = llvm::dyn_cast<clang::BuiltinType>(
+ qual_type->getCanonicalTypeInternal())) {
+ clang::BuiltinType::Kind kind = BT->getKind();
+ if (kind >= clang::BuiltinType::Float &&
+ kind <= clang::BuiltinType::LongDouble) {
+ count = 1;
+ is_complex = false;
+ return true;
+ }
+ } else if (const clang::ComplexType *CT =
+ llvm::dyn_cast<clang::ComplexType>(
+ qual_type->getCanonicalTypeInternal())) {
+ if (IsFloatingPointType(CT->getElementType().getAsOpaquePtr(), count,
+ is_complex)) {
+ count = 2;
+ is_complex = true;
+ return true;
+ }
+ } else if (const clang::VectorType *VT = llvm::dyn_cast<clang::VectorType>(
+ qual_type->getCanonicalTypeInternal())) {
+ if (IsFloatingPointType(VT->getElementType().getAsOpaquePtr(), count,
+ is_complex)) {
+ count = VT->getNumElements();
+ is_complex = false;
+ return true;
+ }
}
- count = 0;
- is_complex = false;
- return false;
+ }
+ count = 0;
+ is_complex = false;
+ return false;
}
+bool ClangASTContext::IsDefined(lldb::opaque_compiler_type_t type) {
+ if (!type)
+ return false;
-bool
-ClangASTContext::IsDefined(lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return false;
-
- clang::QualType qual_type(GetQualType(type));
- const clang::TagType *tag_type = llvm::dyn_cast<clang::TagType>(qual_type.getTypePtr());
- if (tag_type)
- {
- clang::TagDecl *tag_decl = tag_type->getDecl();
- if (tag_decl)
- return tag_decl->isCompleteDefinition();
- return false;
- }
- else
- {
- const clang::ObjCObjectType *objc_class_type = llvm::dyn_cast<clang::ObjCObjectType>(qual_type);
- if (objc_class_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
- if (class_interface_decl)
- return class_interface_decl->getDefinition() != nullptr;
- return false;
- }
+ clang::QualType qual_type(GetQualType(type));
+ const clang::TagType *tag_type =
+ llvm::dyn_cast<clang::TagType>(qual_type.getTypePtr());
+ if (tag_type) {
+ clang::TagDecl *tag_decl = tag_type->getDecl();
+ if (tag_decl)
+ return tag_decl->isCompleteDefinition();
+ return false;
+ } else {
+ const clang::ObjCObjectType *objc_class_type =
+ llvm::dyn_cast<clang::ObjCObjectType>(qual_type);
+ if (objc_class_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterface();
+ if (class_interface_decl)
+ return class_interface_decl->getDefinition() != nullptr;
+ return false;
}
- return true;
+ }
+ return true;
}
-bool
-ClangASTContext::IsObjCClassType (const CompilerType& type)
-{
- if (type)
- {
- clang::QualType qual_type(ClangUtil::GetCanonicalQualType(type));
+bool ClangASTContext::IsObjCClassType(const CompilerType &type) {
+ if (type) {
+ clang::QualType qual_type(ClangUtil::GetCanonicalQualType(type));
- const clang::ObjCObjectPointerType *obj_pointer_type = llvm::dyn_cast<clang::ObjCObjectPointerType>(qual_type);
-
- if (obj_pointer_type)
- return obj_pointer_type->isObjCClassType();
- }
- return false;
+ const clang::ObjCObjectPointerType *obj_pointer_type =
+ llvm::dyn_cast<clang::ObjCObjectPointerType>(qual_type);
+
+ if (obj_pointer_type)
+ return obj_pointer_type->isObjCClassType();
+ }
+ return false;
+}
+
+bool ClangASTContext::IsObjCObjectOrInterfaceType(const CompilerType &type) {
+ if (ClangUtil::IsClangType(type))
+ return ClangUtil::GetCanonicalQualType(type)->isObjCObjectOrInterfaceType();
+ return false;
}
-bool
-ClangASTContext::IsObjCObjectOrInterfaceType (const CompilerType& type)
-{
- if (ClangUtil::IsClangType(type))
- return ClangUtil::GetCanonicalQualType(type)->isObjCObjectOrInterfaceType();
+bool ClangASTContext::IsClassType(lldb::opaque_compiler_type_t type) {
+ if (!type)
return false;
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ return (type_class == clang::Type::Record);
}
-bool
-ClangASTContext::IsClassType(lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return false;
- clang::QualType qual_type(GetCanonicalQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- return (type_class == clang::Type::Record);
+bool ClangASTContext::IsEnumType(lldb::opaque_compiler_type_t type) {
+ if (!type)
+ return false;
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ return (type_class == clang::Type::Enum);
}
-bool
-ClangASTContext::IsEnumType(lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return false;
+bool ClangASTContext::IsPolymorphicClass(lldb::opaque_compiler_type_t type) {
+ if (type) {
clang::QualType qual_type(GetCanonicalQualType(type));
const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- return (type_class == clang::Type::Enum);
-}
-
-bool
-ClangASTContext::IsPolymorphicClass(lldb::opaque_compiler_type_t type)
-{
- if (type)
- {
- clang::QualType qual_type(GetCanonicalQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Record:
- if (GetCompleteType(type))
- {
- const clang::RecordType *record_type = llvm::cast<clang::RecordType>(qual_type.getTypePtr());
- const clang::RecordDecl *record_decl = record_type->getDecl();
- if (record_decl)
- {
- const clang::CXXRecordDecl *cxx_record_decl = llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
- if (cxx_record_decl)
- return cxx_record_decl->isPolymorphic();
- }
- }
- break;
-
- default:
- break;
+ switch (type_class) {
+ case clang::Type::Record:
+ if (GetCompleteType(type)) {
+ const clang::RecordType *record_type =
+ llvm::cast<clang::RecordType>(qual_type.getTypePtr());
+ const clang::RecordDecl *record_decl = record_type->getDecl();
+ if (record_decl) {
+ const clang::CXXRecordDecl *cxx_record_decl =
+ llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
+ if (cxx_record_decl)
+ return cxx_record_decl->isPolymorphic();
}
+ }
+ break;
+
+ default:
+ break;
}
- return false;
+ }
+ return false;
}
-bool
-ClangASTContext::IsPossibleDynamicType (lldb::opaque_compiler_type_t type, CompilerType *dynamic_pointee_type,
- bool check_cplusplus,
- bool check_objc)
-{
- clang::QualType pointee_qual_type;
- if (type)
- {
- clang::QualType qual_type (GetCanonicalQualType(type));
- bool success = false;
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Builtin:
- if (check_objc && llvm::cast<clang::BuiltinType>(qual_type)->getKind() == clang::BuiltinType::ObjCId)
- {
- if (dynamic_pointee_type)
- dynamic_pointee_type->SetCompilerType(this, type);
- return true;
- }
- break;
-
- case clang::Type::ObjCObjectPointer:
- if (check_objc)
- {
- if (auto objc_pointee_type = qual_type->getPointeeType().getTypePtrOrNull())
- {
- if (auto objc_object_type = llvm::dyn_cast_or_null<clang::ObjCObjectType>(objc_pointee_type))
- {
- if (objc_object_type->isObjCClass())
- return false;
- }
- }
- if (dynamic_pointee_type)
- dynamic_pointee_type->SetCompilerType(getASTContext(), llvm::cast<clang::ObjCObjectPointerType>(qual_type)->getPointeeType());
- return true;
- }
- break;
-
- case clang::Type::Pointer:
- pointee_qual_type = llvm::cast<clang::PointerType>(qual_type)->getPointeeType();
- success = true;
- break;
-
- case clang::Type::LValueReference:
- case clang::Type::RValueReference:
- pointee_qual_type = llvm::cast<clang::ReferenceType>(qual_type)->getPointeeType();
- success = true;
- break;
-
- case clang::Type::Typedef:
- return IsPossibleDynamicType (llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(),
- dynamic_pointee_type,
- check_cplusplus,
- check_objc);
-
- case clang::Type::Auto:
- return IsPossibleDynamicType (llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr(),
- dynamic_pointee_type,
- check_cplusplus,
- check_objc);
-
- case clang::Type::Elaborated:
- return IsPossibleDynamicType (llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr(),
- dynamic_pointee_type,
- check_cplusplus,
- check_objc);
-
- case clang::Type::Paren:
- return IsPossibleDynamicType (llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(),
- dynamic_pointee_type,
- check_cplusplus,
- check_objc);
- default:
- break;
+bool ClangASTContext::IsPossibleDynamicType(lldb::opaque_compiler_type_t type,
+ CompilerType *dynamic_pointee_type,
+ bool check_cplusplus,
+ bool check_objc) {
+ clang::QualType pointee_qual_type;
+ if (type) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ bool success = false;
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Builtin:
+ if (check_objc &&
+ llvm::cast<clang::BuiltinType>(qual_type)->getKind() ==
+ clang::BuiltinType::ObjCId) {
+ if (dynamic_pointee_type)
+ dynamic_pointee_type->SetCompilerType(this, type);
+ return true;
+ }
+ break;
+
+ case clang::Type::ObjCObjectPointer:
+ if (check_objc) {
+ if (auto objc_pointee_type =
+ qual_type->getPointeeType().getTypePtrOrNull()) {
+ if (auto objc_object_type =
+ llvm::dyn_cast_or_null<clang::ObjCObjectType>(
+ objc_pointee_type)) {
+ if (objc_object_type->isObjCClass())
+ return false;
+ }
}
-
- if (success)
- {
- // Check to make sure what we are pointing too is a possible dynamic C++ type
- // We currently accept any "void *" (in case we have a class that has been
- // watered down to an opaque pointer) and virtual C++ classes.
- const clang::Type::TypeClass pointee_type_class = pointee_qual_type.getCanonicalType()->getTypeClass();
- switch (pointee_type_class)
- {
- case clang::Type::Builtin:
- switch (llvm::cast<clang::BuiltinType>(pointee_qual_type)->getKind())
- {
- case clang::BuiltinType::UnknownAny:
- case clang::BuiltinType::Void:
- if (dynamic_pointee_type)
- dynamic_pointee_type->SetCompilerType(getASTContext(), pointee_qual_type);
- return true;
- default:
- break;
- }
- break;
-
- case clang::Type::Record:
- if (check_cplusplus)
- {
- clang::CXXRecordDecl *cxx_record_decl = pointee_qual_type->getAsCXXRecordDecl();
- if (cxx_record_decl)
- {
- bool is_complete = cxx_record_decl->isCompleteDefinition();
-
- if (is_complete)
- success = cxx_record_decl->isDynamicClass();
- else
- {
- ClangASTMetadata *metadata = ClangASTContext::GetMetadata (getASTContext(), cxx_record_decl);
- if (metadata)
- success = metadata->GetIsDynamicCXXType();
- else
- {
- is_complete = CompilerType(getASTContext(), pointee_qual_type).GetCompleteType();
- if (is_complete)
- success = cxx_record_decl->isDynamicClass();
- else
- success = false;
- }
- }
-
- if (success)
- {
- if (dynamic_pointee_type)
- dynamic_pointee_type->SetCompilerType(getASTContext(), pointee_qual_type);
- return true;
- }
- }
- }
- break;
-
- case clang::Type::ObjCObject:
- case clang::Type::ObjCInterface:
- if (check_objc)
- {
- if (dynamic_pointee_type)
- dynamic_pointee_type->SetCompilerType(getASTContext(), pointee_qual_type);
- return true;
- }
- break;
-
- default:
- break;
+ if (dynamic_pointee_type)
+ dynamic_pointee_type->SetCompilerType(
+ getASTContext(),
+ llvm::cast<clang::ObjCObjectPointerType>(qual_type)
+ ->getPointeeType());
+ return true;
+ }
+ break;
+
+ case clang::Type::Pointer:
+ pointee_qual_type =
+ llvm::cast<clang::PointerType>(qual_type)->getPointeeType();
+ success = true;
+ break;
+
+ case clang::Type::LValueReference:
+ case clang::Type::RValueReference:
+ pointee_qual_type =
+ llvm::cast<clang::ReferenceType>(qual_type)->getPointeeType();
+ success = true;
+ break;
+
+ case clang::Type::Typedef:
+ return IsPossibleDynamicType(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr(),
+ dynamic_pointee_type, check_cplusplus,
+ check_objc);
+
+ case clang::Type::Auto:
+ return IsPossibleDynamicType(llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr(),
+ dynamic_pointee_type, check_cplusplus,
+ check_objc);
+
+ case clang::Type::Elaborated:
+ return IsPossibleDynamicType(llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr(),
+ dynamic_pointee_type, check_cplusplus,
+ check_objc);
+
+ case clang::Type::Paren:
+ return IsPossibleDynamicType(
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(),
+ dynamic_pointee_type, check_cplusplus, check_objc);
+ default:
+ break;
+ }
+
+ if (success) {
+ // Check to make sure what we are pointing too is a possible dynamic C++
+ // type
+ // We currently accept any "void *" (in case we have a class that has been
+ // watered down to an opaque pointer) and virtual C++ classes.
+ const clang::Type::TypeClass pointee_type_class =
+ pointee_qual_type.getCanonicalType()->getTypeClass();
+ switch (pointee_type_class) {
+ case clang::Type::Builtin:
+ switch (llvm::cast<clang::BuiltinType>(pointee_qual_type)->getKind()) {
+ case clang::BuiltinType::UnknownAny:
+ case clang::BuiltinType::Void:
+ if (dynamic_pointee_type)
+ dynamic_pointee_type->SetCompilerType(getASTContext(),
+ pointee_qual_type);
+ return true;
+ default:
+ break;
+ }
+ break;
+
+ case clang::Type::Record:
+ if (check_cplusplus) {
+ clang::CXXRecordDecl *cxx_record_decl =
+ pointee_qual_type->getAsCXXRecordDecl();
+ if (cxx_record_decl) {
+ bool is_complete = cxx_record_decl->isCompleteDefinition();
+
+ if (is_complete)
+ success = cxx_record_decl->isDynamicClass();
+ else {
+ ClangASTMetadata *metadata = ClangASTContext::GetMetadata(
+ getASTContext(), cxx_record_decl);
+ if (metadata)
+ success = metadata->GetIsDynamicCXXType();
+ else {
+ is_complete = CompilerType(getASTContext(), pointee_qual_type)
+ .GetCompleteType();
+ if (is_complete)
+ success = cxx_record_decl->isDynamicClass();
+ else
+ success = false;
+ }
+ }
+
+ if (success) {
+ if (dynamic_pointee_type)
+ dynamic_pointee_type->SetCompilerType(getASTContext(),
+ pointee_qual_type);
+ return true;
}
+ }
+ }
+ break;
+
+ case clang::Type::ObjCObject:
+ case clang::Type::ObjCInterface:
+ if (check_objc) {
+ if (dynamic_pointee_type)
+ dynamic_pointee_type->SetCompilerType(getASTContext(),
+ pointee_qual_type);
+ return true;
}
+ break;
+
+ default:
+ break;
+ }
}
- if (dynamic_pointee_type)
- dynamic_pointee_type->Clear();
- return false;
+ }
+ if (dynamic_pointee_type)
+ dynamic_pointee_type->Clear();
+ return false;
}
+bool ClangASTContext::IsScalarType(lldb::opaque_compiler_type_t type) {
+ if (!type)
+ return false;
-bool
-ClangASTContext::IsScalarType (lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return false;
-
- return (GetTypeInfo (type, nullptr) & eTypeIsScalar) != 0;
+ return (GetTypeInfo(type, nullptr) & eTypeIsScalar) != 0;
}
-bool
-ClangASTContext::IsTypedefType (lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return false;
- return GetQualType(type)->getTypeClass() == clang::Type::Typedef;
+bool ClangASTContext::IsTypedefType(lldb::opaque_compiler_type_t type) {
+ if (!type)
+ return false;
+ return GetQualType(type)->getTypeClass() == clang::Type::Typedef;
}
-bool
-ClangASTContext::IsVoidType (lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return false;
- return GetCanonicalQualType(type)->isVoidType();
-}
-
-bool
-ClangASTContext::SupportsLanguage (lldb::LanguageType language)
-{
- return ClangASTContextSupportsLanguage(language);
-}
-
-bool
-ClangASTContext::GetCXXClassName (const CompilerType& type, std::string &class_name)
-{
- if (type)
- {
- clang::QualType qual_type(ClangUtil::GetCanonicalQualType(type));
- if (!qual_type.isNull())
- {
- clang::CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
- if (cxx_record_decl)
- {
- class_name.assign(cxx_record_decl->getIdentifier()->getNameStart());
- return true;
- }
- }
- }
- class_name.clear();
+bool ClangASTContext::IsVoidType(lldb::opaque_compiler_type_t type) {
+ if (!type)
return false;
+ return GetCanonicalQualType(type)->isVoidType();
}
+bool ClangASTContext::SupportsLanguage(lldb::LanguageType language) {
+ return ClangASTContextSupportsLanguage(language);
+}
-bool
-ClangASTContext::IsCXXClassType (const CompilerType& type)
-{
- if (!type)
- return false;
-
+bool ClangASTContext::GetCXXClassName(const CompilerType &type,
+ std::string &class_name) {
+ if (type) {
clang::QualType qual_type(ClangUtil::GetCanonicalQualType(type));
- if (!qual_type.isNull() && qual_type->getAsCXXRecordDecl() != nullptr)
+ if (!qual_type.isNull()) {
+ clang::CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
+ if (cxx_record_decl) {
+ class_name.assign(cxx_record_decl->getIdentifier()->getNameStart());
return true;
+ }
+ }
+ }
+ class_name.clear();
+ return false;
+}
+
+bool ClangASTContext::IsCXXClassType(const CompilerType &type) {
+ if (!type)
return false;
+
+ clang::QualType qual_type(ClangUtil::GetCanonicalQualType(type));
+ if (!qual_type.isNull() && qual_type->getAsCXXRecordDecl() != nullptr)
+ return true;
+ return false;
}
-bool
-ClangASTContext::IsBeingDefined (lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return false;
- clang::QualType qual_type (GetCanonicalQualType(type));
- const clang::TagType *tag_type = llvm::dyn_cast<clang::TagType>(qual_type);
- if (tag_type)
- return tag_type->isBeingDefined();
+bool ClangASTContext::IsBeingDefined(lldb::opaque_compiler_type_t type) {
+ if (!type)
return false;
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::TagType *tag_type = llvm::dyn_cast<clang::TagType>(qual_type);
+ if (tag_type)
+ return tag_type->isBeingDefined();
+ return false;
}
-bool
-ClangASTContext::IsObjCObjectPointerType (const CompilerType& type, CompilerType *class_type_ptr)
-{
- if (!type)
- return false;
+bool ClangASTContext::IsObjCObjectPointerType(const CompilerType &type,
+ CompilerType *class_type_ptr) {
+ if (!type)
+ return false;
- clang::QualType qual_type(ClangUtil::GetCanonicalQualType(type));
+ clang::QualType qual_type(ClangUtil::GetCanonicalQualType(type));
- if (!qual_type.isNull() && qual_type->isObjCObjectPointerType())
- {
- if (class_type_ptr)
- {
- if (!qual_type->isObjCClassType() &&
- !qual_type->isObjCIdType())
- {
- const clang::ObjCObjectPointerType *obj_pointer_type = llvm::dyn_cast<clang::ObjCObjectPointerType>(qual_type);
- if (obj_pointer_type == nullptr)
- class_type_ptr->Clear();
- else
- class_type_ptr->SetCompilerType (type.GetTypeSystem(), clang::QualType(obj_pointer_type->getInterfaceType(), 0).getAsOpaquePtr());
- }
- }
- return true;
+ if (!qual_type.isNull() && qual_type->isObjCObjectPointerType()) {
+ if (class_type_ptr) {
+ if (!qual_type->isObjCClassType() && !qual_type->isObjCIdType()) {
+ const clang::ObjCObjectPointerType *obj_pointer_type =
+ llvm::dyn_cast<clang::ObjCObjectPointerType>(qual_type);
+ if (obj_pointer_type == nullptr)
+ class_type_ptr->Clear();
+ else
+ class_type_ptr->SetCompilerType(
+ type.GetTypeSystem(),
+ clang::QualType(obj_pointer_type->getInterfaceType(), 0)
+ .getAsOpaquePtr());
+ }
}
- if (class_type_ptr)
- class_type_ptr->Clear();
- return false;
+ return true;
+ }
+ if (class_type_ptr)
+ class_type_ptr->Clear();
+ return false;
}
-bool
-ClangASTContext::GetObjCClassName (const CompilerType& type, std::string &class_name)
-{
- if (!type)
- return false;
+bool ClangASTContext::GetObjCClassName(const CompilerType &type,
+ std::string &class_name) {
+ if (!type)
+ return false;
- clang::QualType qual_type(ClangUtil::GetCanonicalQualType(type));
+ clang::QualType qual_type(ClangUtil::GetCanonicalQualType(type));
- const clang::ObjCObjectType *object_type = llvm::dyn_cast<clang::ObjCObjectType>(qual_type);
- if (object_type)
- {
- const clang::ObjCInterfaceDecl *interface = object_type->getInterface();
- if (interface)
- {
- class_name = interface->getNameAsString();
- return true;
- }
+ const clang::ObjCObjectType *object_type =
+ llvm::dyn_cast<clang::ObjCObjectType>(qual_type);
+ if (object_type) {
+ const clang::ObjCInterfaceDecl *interface = object_type->getInterface();
+ if (interface) {
+ class_name = interface->getNameAsString();
+ return true;
}
- return false;
+ }
+ return false;
}
-
//----------------------------------------------------------------------
// Type Completion
//----------------------------------------------------------------------
-bool
-ClangASTContext::GetCompleteType (lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return false;
- const bool allow_completion = true;
- return GetCompleteQualType (getASTContext(), GetQualType(type), allow_completion);
+bool ClangASTContext::GetCompleteType(lldb::opaque_compiler_type_t type) {
+ if (!type)
+ return false;
+ const bool allow_completion = true;
+ return GetCompleteQualType(getASTContext(), GetQualType(type),
+ allow_completion);
}
-ConstString
-ClangASTContext::GetTypeName (lldb::opaque_compiler_type_t type)
-{
- std::string type_name;
- if (type)
- {
- clang::PrintingPolicy printing_policy (getASTContext()->getPrintingPolicy());
- clang::QualType qual_type(GetQualType(type));
- printing_policy.SuppressTagKeyword = true;
- const clang::TypedefType *typedef_type = qual_type->getAs<clang::TypedefType>();
- if (typedef_type)
- {
- const clang::TypedefNameDecl *typedef_decl = typedef_type->getDecl();
- type_name = typedef_decl->getQualifiedNameAsString();
- }
- else
- {
- type_name = qual_type.getAsString(printing_policy);
- }
+ConstString ClangASTContext::GetTypeName(lldb::opaque_compiler_type_t type) {
+ std::string type_name;
+ if (type) {
+ clang::PrintingPolicy printing_policy(getASTContext()->getPrintingPolicy());
+ clang::QualType qual_type(GetQualType(type));
+ printing_policy.SuppressTagKeyword = true;
+ const clang::TypedefType *typedef_type =
+ qual_type->getAs<clang::TypedefType>();
+ if (typedef_type) {
+ const clang::TypedefNameDecl *typedef_decl = typedef_type->getDecl();
+ type_name = typedef_decl->getQualifiedNameAsString();
+ } else {
+ type_name = qual_type.getAsString(printing_policy);
}
- return ConstString(type_name);
+ }
+ return ConstString(type_name);
}
uint32_t
-ClangASTContext::GetTypeInfo (lldb::opaque_compiler_type_t type, CompilerType *pointee_or_element_clang_type)
-{
- if (!type)
- return 0;
-
- if (pointee_or_element_clang_type)
- pointee_or_element_clang_type->Clear();
-
- clang::QualType qual_type (GetQualType(type));
-
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Builtin:
- {
- const clang::BuiltinType *builtin_type = llvm::dyn_cast<clang::BuiltinType>(qual_type->getCanonicalTypeInternal());
-
- uint32_t builtin_type_flags = eTypeIsBuiltIn | eTypeHasValue;
- switch (builtin_type->getKind())
- {
- case clang::BuiltinType::ObjCId:
- case clang::BuiltinType::ObjCClass:
- if (pointee_or_element_clang_type)
- pointee_or_element_clang_type->SetCompilerType(getASTContext(), getASTContext()->ObjCBuiltinClassTy);
- builtin_type_flags |= eTypeIsPointer | eTypeIsObjC;
- break;
-
- case clang::BuiltinType::ObjCSel:
- if (pointee_or_element_clang_type)
- pointee_or_element_clang_type->SetCompilerType(getASTContext(), getASTContext()->CharTy);
- builtin_type_flags |= eTypeIsPointer | eTypeIsObjC;
- break;
-
- case clang::BuiltinType::Bool:
- case clang::BuiltinType::Char_U:
- case clang::BuiltinType::UChar:
- case clang::BuiltinType::WChar_U:
- case clang::BuiltinType::Char16:
- case clang::BuiltinType::Char32:
- case clang::BuiltinType::UShort:
- case clang::BuiltinType::UInt:
- case clang::BuiltinType::ULong:
- case clang::BuiltinType::ULongLong:
- case clang::BuiltinType::UInt128:
- case clang::BuiltinType::Char_S:
- case clang::BuiltinType::SChar:
- case clang::BuiltinType::WChar_S:
- case clang::BuiltinType::Short:
- case clang::BuiltinType::Int:
- case clang::BuiltinType::Long:
- case clang::BuiltinType::LongLong:
- case clang::BuiltinType::Int128:
- case clang::BuiltinType::Float:
- case clang::BuiltinType::Double:
- case clang::BuiltinType::LongDouble:
- builtin_type_flags |= eTypeIsScalar;
- if (builtin_type->isInteger())
- {
- builtin_type_flags |= eTypeIsInteger;
- if (builtin_type->isSignedInteger())
- builtin_type_flags |= eTypeIsSigned;
- }
- else if (builtin_type->isFloatingPoint())
- builtin_type_flags |= eTypeIsFloat;
- break;
- default:
- break;
- }
- return builtin_type_flags;
- }
-
- case clang::Type::BlockPointer:
- if (pointee_or_element_clang_type)
- pointee_or_element_clang_type->SetCompilerType(getASTContext(), qual_type->getPointeeType());
- return eTypeIsPointer | eTypeHasChildren | eTypeIsBlock;
-
- case clang::Type::Complex:
- {
- uint32_t complex_type_flags = eTypeIsBuiltIn | eTypeHasValue | eTypeIsComplex;
- const clang::ComplexType *complex_type = llvm::dyn_cast<clang::ComplexType>(qual_type->getCanonicalTypeInternal());
- if (complex_type)
- {
- clang::QualType complex_element_type (complex_type->getElementType());
- if (complex_element_type->isIntegerType())
- complex_type_flags |= eTypeIsFloat;
- else if (complex_element_type->isFloatingType())
- complex_type_flags |= eTypeIsInteger;
- }
- return complex_type_flags;
- }
- break;
-
- case clang::Type::ConstantArray:
- case clang::Type::DependentSizedArray:
- case clang::Type::IncompleteArray:
- case clang::Type::VariableArray:
- if (pointee_or_element_clang_type)
- pointee_or_element_clang_type->SetCompilerType(getASTContext(), llvm::cast<clang::ArrayType>(qual_type.getTypePtr())->getElementType());
- return eTypeHasChildren | eTypeIsArray;
-
- case clang::Type::DependentName: return 0;
- case clang::Type::DependentSizedExtVector: return eTypeHasChildren | eTypeIsVector;
- case clang::Type::DependentTemplateSpecialization: return eTypeIsTemplate;
- case clang::Type::Decltype: return 0;
-
- case clang::Type::Enum:
- if (pointee_or_element_clang_type)
- pointee_or_element_clang_type->SetCompilerType(getASTContext(), llvm::cast<clang::EnumType>(qual_type)->getDecl()->getIntegerType());
- return eTypeIsEnumeration | eTypeHasValue;
-
- case clang::Type::Auto:
- return CompilerType (getASTContext(), llvm::cast<clang::AutoType>(qual_type)->getDeducedType()).GetTypeInfo (pointee_or_element_clang_type);
- case clang::Type::Elaborated:
- return CompilerType (getASTContext(), llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType()).GetTypeInfo (pointee_or_element_clang_type);
- case clang::Type::Paren:
- return CompilerType (getASTContext(), llvm::cast<clang::ParenType>(qual_type)->desugar()).GetTypeInfo (pointee_or_element_clang_type);
-
- case clang::Type::FunctionProto: return eTypeIsFuncPrototype | eTypeHasValue;
- case clang::Type::FunctionNoProto: return eTypeIsFuncPrototype | eTypeHasValue;
- case clang::Type::InjectedClassName: return 0;
-
- case clang::Type::LValueReference:
- case clang::Type::RValueReference:
- if (pointee_or_element_clang_type)
- pointee_or_element_clang_type->SetCompilerType(getASTContext(), llvm::cast<clang::ReferenceType>(qual_type.getTypePtr())->getPointeeType());
- return eTypeHasChildren | eTypeIsReference | eTypeHasValue;
-
- case clang::Type::MemberPointer: return eTypeIsPointer | eTypeIsMember | eTypeHasValue;
-
- case clang::Type::ObjCObjectPointer:
- if (pointee_or_element_clang_type)
- pointee_or_element_clang_type->SetCompilerType(getASTContext(), qual_type->getPointeeType());
- return eTypeHasChildren | eTypeIsObjC | eTypeIsClass | eTypeIsPointer | eTypeHasValue;
-
- case clang::Type::ObjCObject: return eTypeHasChildren | eTypeIsObjC | eTypeIsClass;
- case clang::Type::ObjCInterface: return eTypeHasChildren | eTypeIsObjC | eTypeIsClass;
-
- case clang::Type::Pointer:
- if (pointee_or_element_clang_type)
- pointee_or_element_clang_type->SetCompilerType(getASTContext(), qual_type->getPointeeType());
- return eTypeHasChildren | eTypeIsPointer | eTypeHasValue;
-
- case clang::Type::Record:
- if (qual_type->getAsCXXRecordDecl())
- return eTypeHasChildren | eTypeIsClass | eTypeIsCPlusPlus;
- else
- return eTypeHasChildren | eTypeIsStructUnion;
- break;
- case clang::Type::SubstTemplateTypeParm: return eTypeIsTemplate;
- case clang::Type::TemplateTypeParm: return eTypeIsTemplate;
- case clang::Type::TemplateSpecialization: return eTypeIsTemplate;
-
- case clang::Type::Typedef:
- return eTypeIsTypedef | CompilerType (getASTContext(), llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType()).GetTypeInfo (pointee_or_element_clang_type);
- case clang::Type::TypeOfExpr: return 0;
- case clang::Type::TypeOf: return 0;
- case clang::Type::UnresolvedUsing: return 0;
-
- case clang::Type::ExtVector:
- case clang::Type::Vector:
- {
- uint32_t vector_type_flags = eTypeHasChildren | eTypeIsVector;
- const clang::VectorType *vector_type = llvm::dyn_cast<clang::VectorType>(qual_type->getCanonicalTypeInternal());
- if (vector_type)
- {
- if (vector_type->isIntegerType())
- vector_type_flags |= eTypeIsFloat;
- else if (vector_type->isFloatingType())
- vector_type_flags |= eTypeIsInteger;
- }
- return vector_type_flags;
- }
- default: return 0;
+ClangASTContext::GetTypeInfo(lldb::opaque_compiler_type_t type,
+ CompilerType *pointee_or_element_clang_type) {
+ if (!type)
+ return 0;
+
+ if (pointee_or_element_clang_type)
+ pointee_or_element_clang_type->Clear();
+
+ clang::QualType qual_type(GetQualType(type));
+
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Builtin: {
+ const clang::BuiltinType *builtin_type = llvm::dyn_cast<clang::BuiltinType>(
+ qual_type->getCanonicalTypeInternal());
+
+ uint32_t builtin_type_flags = eTypeIsBuiltIn | eTypeHasValue;
+ switch (builtin_type->getKind()) {
+ case clang::BuiltinType::ObjCId:
+ case clang::BuiltinType::ObjCClass:
+ if (pointee_or_element_clang_type)
+ pointee_or_element_clang_type->SetCompilerType(
+ getASTContext(), getASTContext()->ObjCBuiltinClassTy);
+ builtin_type_flags |= eTypeIsPointer | eTypeIsObjC;
+ break;
+
+ case clang::BuiltinType::ObjCSel:
+ if (pointee_or_element_clang_type)
+ pointee_or_element_clang_type->SetCompilerType(getASTContext(),
+ getASTContext()->CharTy);
+ builtin_type_flags |= eTypeIsPointer | eTypeIsObjC;
+ break;
+
+ case clang::BuiltinType::Bool:
+ case clang::BuiltinType::Char_U:
+ case clang::BuiltinType::UChar:
+ case clang::BuiltinType::WChar_U:
+ case clang::BuiltinType::Char16:
+ case clang::BuiltinType::Char32:
+ case clang::BuiltinType::UShort:
+ case clang::BuiltinType::UInt:
+ case clang::BuiltinType::ULong:
+ case clang::BuiltinType::ULongLong:
+ case clang::BuiltinType::UInt128:
+ case clang::BuiltinType::Char_S:
+ case clang::BuiltinType::SChar:
+ case clang::BuiltinType::WChar_S:
+ case clang::BuiltinType::Short:
+ case clang::BuiltinType::Int:
+ case clang::BuiltinType::Long:
+ case clang::BuiltinType::LongLong:
+ case clang::BuiltinType::Int128:
+ case clang::BuiltinType::Float:
+ case clang::BuiltinType::Double:
+ case clang::BuiltinType::LongDouble:
+ builtin_type_flags |= eTypeIsScalar;
+ if (builtin_type->isInteger()) {
+ builtin_type_flags |= eTypeIsInteger;
+ if (builtin_type->isSignedInteger())
+ builtin_type_flags |= eTypeIsSigned;
+ } else if (builtin_type->isFloatingPoint())
+ builtin_type_flags |= eTypeIsFloat;
+ break;
+ default:
+ break;
}
+ return builtin_type_flags;
+ }
+
+ case clang::Type::BlockPointer:
+ if (pointee_or_element_clang_type)
+ pointee_or_element_clang_type->SetCompilerType(
+ getASTContext(), qual_type->getPointeeType());
+ return eTypeIsPointer | eTypeHasChildren | eTypeIsBlock;
+
+ case clang::Type::Complex: {
+ uint32_t complex_type_flags =
+ eTypeIsBuiltIn | eTypeHasValue | eTypeIsComplex;
+ const clang::ComplexType *complex_type = llvm::dyn_cast<clang::ComplexType>(
+ qual_type->getCanonicalTypeInternal());
+ if (complex_type) {
+ clang::QualType complex_element_type(complex_type->getElementType());
+ if (complex_element_type->isIntegerType())
+ complex_type_flags |= eTypeIsFloat;
+ else if (complex_element_type->isFloatingType())
+ complex_type_flags |= eTypeIsInteger;
+ }
+ return complex_type_flags;
+ } break;
+
+ case clang::Type::ConstantArray:
+ case clang::Type::DependentSizedArray:
+ case clang::Type::IncompleteArray:
+ case clang::Type::VariableArray:
+ if (pointee_or_element_clang_type)
+ pointee_or_element_clang_type->SetCompilerType(
+ getASTContext(), llvm::cast<clang::ArrayType>(qual_type.getTypePtr())
+ ->getElementType());
+ return eTypeHasChildren | eTypeIsArray;
+
+ case clang::Type::DependentName:
+ return 0;
+ case clang::Type::DependentSizedExtVector:
+ return eTypeHasChildren | eTypeIsVector;
+ case clang::Type::DependentTemplateSpecialization:
+ return eTypeIsTemplate;
+ case clang::Type::Decltype:
return 0;
-}
+ case clang::Type::Enum:
+ if (pointee_or_element_clang_type)
+ pointee_or_element_clang_type->SetCompilerType(
+ getASTContext(),
+ llvm::cast<clang::EnumType>(qual_type)->getDecl()->getIntegerType());
+ return eTypeIsEnumeration | eTypeHasValue;
+
+ case clang::Type::Auto:
+ return CompilerType(
+ getASTContext(),
+ llvm::cast<clang::AutoType>(qual_type)->getDeducedType())
+ .GetTypeInfo(pointee_or_element_clang_type);
+ case clang::Type::Elaborated:
+ return CompilerType(
+ getASTContext(),
+ llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType())
+ .GetTypeInfo(pointee_or_element_clang_type);
+ case clang::Type::Paren:
+ return CompilerType(getASTContext(),
+ llvm::cast<clang::ParenType>(qual_type)->desugar())
+ .GetTypeInfo(pointee_or_element_clang_type);
+
+ case clang::Type::FunctionProto:
+ return eTypeIsFuncPrototype | eTypeHasValue;
+ case clang::Type::FunctionNoProto:
+ return eTypeIsFuncPrototype | eTypeHasValue;
+ case clang::Type::InjectedClassName:
+ return 0;
+ case clang::Type::LValueReference:
+ case clang::Type::RValueReference:
+ if (pointee_or_element_clang_type)
+ pointee_or_element_clang_type->SetCompilerType(
+ getASTContext(),
+ llvm::cast<clang::ReferenceType>(qual_type.getTypePtr())
+ ->getPointeeType());
+ return eTypeHasChildren | eTypeIsReference | eTypeHasValue;
-lldb::LanguageType
-ClangASTContext::GetMinimumLanguage (lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return lldb::eLanguageTypeC;
-
- // If the type is a reference, then resolve it to what it refers to first:
- clang::QualType qual_type (GetCanonicalQualType(type).getNonReferenceType());
- if (qual_type->isAnyPointerType())
- {
- if (qual_type->isObjCObjectPointerType())
- return lldb::eLanguageTypeObjC;
-
- clang::QualType pointee_type (qual_type->getPointeeType());
- if (pointee_type->getPointeeCXXRecordDecl() != nullptr)
- return lldb::eLanguageTypeC_plus_plus;
- if (pointee_type->isObjCObjectOrInterfaceType())
- return lldb::eLanguageTypeObjC;
- if (pointee_type->isObjCClassType())
- return lldb::eLanguageTypeObjC;
- if (pointee_type.getTypePtr() == getASTContext()->ObjCBuiltinIdTy.getTypePtr())
- return lldb::eLanguageTypeObjC;
- }
+ case clang::Type::MemberPointer:
+ return eTypeIsPointer | eTypeIsMember | eTypeHasValue;
+
+ case clang::Type::ObjCObjectPointer:
+ if (pointee_or_element_clang_type)
+ pointee_or_element_clang_type->SetCompilerType(
+ getASTContext(), qual_type->getPointeeType());
+ return eTypeHasChildren | eTypeIsObjC | eTypeIsClass | eTypeIsPointer |
+ eTypeHasValue;
+
+ case clang::Type::ObjCObject:
+ return eTypeHasChildren | eTypeIsObjC | eTypeIsClass;
+ case clang::Type::ObjCInterface:
+ return eTypeHasChildren | eTypeIsObjC | eTypeIsClass;
+
+ case clang::Type::Pointer:
+ if (pointee_or_element_clang_type)
+ pointee_or_element_clang_type->SetCompilerType(
+ getASTContext(), qual_type->getPointeeType());
+ return eTypeHasChildren | eTypeIsPointer | eTypeHasValue;
+
+ case clang::Type::Record:
+ if (qual_type->getAsCXXRecordDecl())
+ return eTypeHasChildren | eTypeIsClass | eTypeIsCPlusPlus;
else
- {
- if (qual_type->isObjCObjectOrInterfaceType())
- return lldb::eLanguageTypeObjC;
- if (qual_type->getAsCXXRecordDecl())
- return lldb::eLanguageTypeC_plus_plus;
- switch (qual_type->getTypeClass())
- {
- default:
- break;
- case clang::Type::Builtin:
- switch (llvm::cast<clang::BuiltinType>(qual_type)->getKind())
- {
- default:
- case clang::BuiltinType::Void:
- case clang::BuiltinType::Bool:
- case clang::BuiltinType::Char_U:
- case clang::BuiltinType::UChar:
- case clang::BuiltinType::WChar_U:
- case clang::BuiltinType::Char16:
- case clang::BuiltinType::Char32:
- case clang::BuiltinType::UShort:
- case clang::BuiltinType::UInt:
- case clang::BuiltinType::ULong:
- case clang::BuiltinType::ULongLong:
- case clang::BuiltinType::UInt128:
- case clang::BuiltinType::Char_S:
- case clang::BuiltinType::SChar:
- case clang::BuiltinType::WChar_S:
- case clang::BuiltinType::Short:
- case clang::BuiltinType::Int:
- case clang::BuiltinType::Long:
- case clang::BuiltinType::LongLong:
- case clang::BuiltinType::Int128:
- case clang::BuiltinType::Float:
- case clang::BuiltinType::Double:
- case clang::BuiltinType::LongDouble:
- break;
-
- case clang::BuiltinType::NullPtr:
- return eLanguageTypeC_plus_plus;
-
- case clang::BuiltinType::ObjCId:
- case clang::BuiltinType::ObjCClass:
- case clang::BuiltinType::ObjCSel:
- return eLanguageTypeObjC;
-
- case clang::BuiltinType::Dependent:
- case clang::BuiltinType::Overload:
- case clang::BuiltinType::BoundMember:
- case clang::BuiltinType::UnknownAny:
- break;
- }
- break;
- case clang::Type::Typedef:
- return CompilerType(getASTContext(), llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType()).GetMinimumLanguage();
- }
- }
+ return eTypeHasChildren | eTypeIsStructUnion;
+ break;
+ case clang::Type::SubstTemplateTypeParm:
+ return eTypeIsTemplate;
+ case clang::Type::TemplateTypeParm:
+ return eTypeIsTemplate;
+ case clang::Type::TemplateSpecialization:
+ return eTypeIsTemplate;
+
+ case clang::Type::Typedef:
+ return eTypeIsTypedef |
+ CompilerType(getASTContext(),
+ llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType())
+ .GetTypeInfo(pointee_or_element_clang_type);
+ case clang::Type::TypeOfExpr:
+ return 0;
+ case clang::Type::TypeOf:
+ return 0;
+ case clang::Type::UnresolvedUsing:
+ return 0;
+
+ case clang::Type::ExtVector:
+ case clang::Type::Vector: {
+ uint32_t vector_type_flags = eTypeHasChildren | eTypeIsVector;
+ const clang::VectorType *vector_type = llvm::dyn_cast<clang::VectorType>(
+ qual_type->getCanonicalTypeInternal());
+ if (vector_type) {
+ if (vector_type->isIntegerType())
+ vector_type_flags |= eTypeIsFloat;
+ else if (vector_type->isFloatingType())
+ vector_type_flags |= eTypeIsInteger;
+ }
+ return vector_type_flags;
+ }
+ default:
+ return 0;
+ }
+ return 0;
+}
+
+lldb::LanguageType
+ClangASTContext::GetMinimumLanguage(lldb::opaque_compiler_type_t type) {
+ if (!type)
return lldb::eLanguageTypeC;
+
+ // If the type is a reference, then resolve it to what it refers to first:
+ clang::QualType qual_type(GetCanonicalQualType(type).getNonReferenceType());
+ if (qual_type->isAnyPointerType()) {
+ if (qual_type->isObjCObjectPointerType())
+ return lldb::eLanguageTypeObjC;
+
+ clang::QualType pointee_type(qual_type->getPointeeType());
+ if (pointee_type->getPointeeCXXRecordDecl() != nullptr)
+ return lldb::eLanguageTypeC_plus_plus;
+ if (pointee_type->isObjCObjectOrInterfaceType())
+ return lldb::eLanguageTypeObjC;
+ if (pointee_type->isObjCClassType())
+ return lldb::eLanguageTypeObjC;
+ if (pointee_type.getTypePtr() ==
+ getASTContext()->ObjCBuiltinIdTy.getTypePtr())
+ return lldb::eLanguageTypeObjC;
+ } else {
+ if (qual_type->isObjCObjectOrInterfaceType())
+ return lldb::eLanguageTypeObjC;
+ if (qual_type->getAsCXXRecordDecl())
+ return lldb::eLanguageTypeC_plus_plus;
+ switch (qual_type->getTypeClass()) {
+ default:
+ break;
+ case clang::Type::Builtin:
+ switch (llvm::cast<clang::BuiltinType>(qual_type)->getKind()) {
+ default:
+ case clang::BuiltinType::Void:
+ case clang::BuiltinType::Bool:
+ case clang::BuiltinType::Char_U:
+ case clang::BuiltinType::UChar:
+ case clang::BuiltinType::WChar_U:
+ case clang::BuiltinType::Char16:
+ case clang::BuiltinType::Char32:
+ case clang::BuiltinType::UShort:
+ case clang::BuiltinType::UInt:
+ case clang::BuiltinType::ULong:
+ case clang::BuiltinType::ULongLong:
+ case clang::BuiltinType::UInt128:
+ case clang::BuiltinType::Char_S:
+ case clang::BuiltinType::SChar:
+ case clang::BuiltinType::WChar_S:
+ case clang::BuiltinType::Short:
+ case clang::BuiltinType::Int:
+ case clang::BuiltinType::Long:
+ case clang::BuiltinType::LongLong:
+ case clang::BuiltinType::Int128:
+ case clang::BuiltinType::Float:
+ case clang::BuiltinType::Double:
+ case clang::BuiltinType::LongDouble:
+ break;
+
+ case clang::BuiltinType::NullPtr:
+ return eLanguageTypeC_plus_plus;
+
+ case clang::BuiltinType::ObjCId:
+ case clang::BuiltinType::ObjCClass:
+ case clang::BuiltinType::ObjCSel:
+ return eLanguageTypeObjC;
+
+ case clang::BuiltinType::Dependent:
+ case clang::BuiltinType::Overload:
+ case clang::BuiltinType::BoundMember:
+ case clang::BuiltinType::UnknownAny:
+ break;
+ }
+ break;
+ case clang::Type::Typedef:
+ return CompilerType(getASTContext(),
+ llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType())
+ .GetMinimumLanguage();
+ }
+ }
+ return lldb::eLanguageTypeC;
}
lldb::TypeClass
-ClangASTContext::GetTypeClass (lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return lldb::eTypeClassInvalid;
-
- clang::QualType qual_type(GetQualType(type));
-
- switch (qual_type->getTypeClass())
- {
- case clang::Type::UnaryTransform: break;
- case clang::Type::FunctionNoProto: return lldb::eTypeClassFunction;
- case clang::Type::FunctionProto: return lldb::eTypeClassFunction;
- case clang::Type::IncompleteArray: return lldb::eTypeClassArray;
- case clang::Type::VariableArray: return lldb::eTypeClassArray;
- case clang::Type::ConstantArray: return lldb::eTypeClassArray;
- case clang::Type::DependentSizedArray: return lldb::eTypeClassArray;
- case clang::Type::DependentSizedExtVector: return lldb::eTypeClassVector;
- case clang::Type::ExtVector: return lldb::eTypeClassVector;
- case clang::Type::Vector: return lldb::eTypeClassVector;
- case clang::Type::Builtin: return lldb::eTypeClassBuiltin;
- case clang::Type::ObjCObjectPointer: return lldb::eTypeClassObjCObjectPointer;
- case clang::Type::BlockPointer: return lldb::eTypeClassBlockPointer;
- case clang::Type::Pointer: return lldb::eTypeClassPointer;
- case clang::Type::LValueReference: return lldb::eTypeClassReference;
- case clang::Type::RValueReference: return lldb::eTypeClassReference;
- case clang::Type::MemberPointer: return lldb::eTypeClassMemberPointer;
- case clang::Type::Complex:
- if (qual_type->isComplexType())
- return lldb::eTypeClassComplexFloat;
- else
- return lldb::eTypeClassComplexInteger;
- case clang::Type::ObjCObject: return lldb::eTypeClassObjCObject;
- case clang::Type::ObjCInterface: return lldb::eTypeClassObjCInterface;
- case clang::Type::Record:
- {
- const clang::RecordType *record_type = llvm::cast<clang::RecordType>(qual_type.getTypePtr());
- const clang::RecordDecl *record_decl = record_type->getDecl();
- if (record_decl->isUnion())
- return lldb::eTypeClassUnion;
- else if (record_decl->isStruct())
- return lldb::eTypeClassStruct;
- else
- return lldb::eTypeClassClass;
- }
- break;
- case clang::Type::Enum: return lldb::eTypeClassEnumeration;
- case clang::Type::Typedef: return lldb::eTypeClassTypedef;
- case clang::Type::UnresolvedUsing: break;
- case clang::Type::Paren:
- return CompilerType(getASTContext(), llvm::cast<clang::ParenType>(qual_type)->desugar()).GetTypeClass();
- case clang::Type::Auto:
- return CompilerType(getASTContext(), llvm::cast<clang::AutoType>(qual_type)->getDeducedType()).GetTypeClass();
- case clang::Type::Elaborated:
- return CompilerType(getASTContext(), llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType()).GetTypeClass();
-
- case clang::Type::Attributed: break;
- case clang::Type::TemplateTypeParm: break;
- case clang::Type::SubstTemplateTypeParm: break;
- case clang::Type::SubstTemplateTypeParmPack:break;
- case clang::Type::InjectedClassName: break;
- case clang::Type::DependentName: break;
- case clang::Type::DependentTemplateSpecialization: break;
- case clang::Type::PackExpansion: break;
-
- case clang::Type::TypeOfExpr: break;
- case clang::Type::TypeOf: break;
- case clang::Type::Decltype: break;
- case clang::Type::TemplateSpecialization: break;
- case clang::Type::Atomic: break;
- case clang::Type::Pipe: break;
-
- // pointer type decayed from an array or function type.
- case clang::Type::Decayed: break;
- case clang::Type::Adjusted: break;
- }
- // We don't know hot to display this type...
- return lldb::eTypeClassOther;
-
-}
-
-unsigned
-ClangASTContext::GetTypeQualifiers(lldb::opaque_compiler_type_t type)
-{
- if (type)
- return GetQualType(type).getQualifiers().getCVRQualifiers();
- return 0;
+ClangASTContext::GetTypeClass(lldb::opaque_compiler_type_t type) {
+ if (!type)
+ return lldb::eTypeClassInvalid;
+
+ clang::QualType qual_type(GetQualType(type));
+
+ switch (qual_type->getTypeClass()) {
+ case clang::Type::UnaryTransform:
+ break;
+ case clang::Type::FunctionNoProto:
+ return lldb::eTypeClassFunction;
+ case clang::Type::FunctionProto:
+ return lldb::eTypeClassFunction;
+ case clang::Type::IncompleteArray:
+ return lldb::eTypeClassArray;
+ case clang::Type::VariableArray:
+ return lldb::eTypeClassArray;
+ case clang::Type::ConstantArray:
+ return lldb::eTypeClassArray;
+ case clang::Type::DependentSizedArray:
+ return lldb::eTypeClassArray;
+ case clang::Type::DependentSizedExtVector:
+ return lldb::eTypeClassVector;
+ case clang::Type::ExtVector:
+ return lldb::eTypeClassVector;
+ case clang::Type::Vector:
+ return lldb::eTypeClassVector;
+ case clang::Type::Builtin:
+ return lldb::eTypeClassBuiltin;
+ case clang::Type::ObjCObjectPointer:
+ return lldb::eTypeClassObjCObjectPointer;
+ case clang::Type::BlockPointer:
+ return lldb::eTypeClassBlockPointer;
+ case clang::Type::Pointer:
+ return lldb::eTypeClassPointer;
+ case clang::Type::LValueReference:
+ return lldb::eTypeClassReference;
+ case clang::Type::RValueReference:
+ return lldb::eTypeClassReference;
+ case clang::Type::MemberPointer:
+ return lldb::eTypeClassMemberPointer;
+ case clang::Type::Complex:
+ if (qual_type->isComplexType())
+ return lldb::eTypeClassComplexFloat;
+ else
+ return lldb::eTypeClassComplexInteger;
+ case clang::Type::ObjCObject:
+ return lldb::eTypeClassObjCObject;
+ case clang::Type::ObjCInterface:
+ return lldb::eTypeClassObjCInterface;
+ case clang::Type::Record: {
+ const clang::RecordType *record_type =
+ llvm::cast<clang::RecordType>(qual_type.getTypePtr());
+ const clang::RecordDecl *record_decl = record_type->getDecl();
+ if (record_decl->isUnion())
+ return lldb::eTypeClassUnion;
+ else if (record_decl->isStruct())
+ return lldb::eTypeClassStruct;
+ else
+ return lldb::eTypeClassClass;
+ } break;
+ case clang::Type::Enum:
+ return lldb::eTypeClassEnumeration;
+ case clang::Type::Typedef:
+ return lldb::eTypeClassTypedef;
+ case clang::Type::UnresolvedUsing:
+ break;
+ case clang::Type::Paren:
+ return CompilerType(getASTContext(),
+ llvm::cast<clang::ParenType>(qual_type)->desugar())
+ .GetTypeClass();
+ case clang::Type::Auto:
+ return CompilerType(
+ getASTContext(),
+ llvm::cast<clang::AutoType>(qual_type)->getDeducedType())
+ .GetTypeClass();
+ case clang::Type::Elaborated:
+ return CompilerType(
+ getASTContext(),
+ llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType())
+ .GetTypeClass();
+
+ case clang::Type::Attributed:
+ break;
+ case clang::Type::TemplateTypeParm:
+ break;
+ case clang::Type::SubstTemplateTypeParm:
+ break;
+ case clang::Type::SubstTemplateTypeParmPack:
+ break;
+ case clang::Type::InjectedClassName:
+ break;
+ case clang::Type::DependentName:
+ break;
+ case clang::Type::DependentTemplateSpecialization:
+ break;
+ case clang::Type::PackExpansion:
+ break;
+
+ case clang::Type::TypeOfExpr:
+ break;
+ case clang::Type::TypeOf:
+ break;
+ case clang::Type::Decltype:
+ break;
+ case clang::Type::TemplateSpecialization:
+ break;
+ case clang::Type::Atomic:
+ break;
+ case clang::Type::Pipe:
+ break;
+
+ // pointer type decayed from an array or function type.
+ case clang::Type::Decayed:
+ break;
+ case clang::Type::Adjusted:
+ break;
+ }
+ // We don't know hot to display this type...
+ return lldb::eTypeClassOther;
+}
+
+unsigned ClangASTContext::GetTypeQualifiers(lldb::opaque_compiler_type_t type) {
+ if (type)
+ return GetQualType(type).getQualifiers().getCVRQualifiers();
+ return 0;
}
//----------------------------------------------------------------------
@@ -4542,1707 +4333,1822 @@ ClangASTContext::GetTypeQualifiers(lldb::opaque_compiler_type_t type)
//----------------------------------------------------------------------
CompilerType
-ClangASTContext::GetArrayElementType (lldb::opaque_compiler_type_t type, uint64_t *stride)
-{
- if (type)
- {
- clang::QualType qual_type(GetCanonicalQualType(type));
-
- const clang::Type *array_eletype = qual_type.getTypePtr()->getArrayElementTypeNoTypeQual();
-
- if (!array_eletype)
- return CompilerType();
-
- CompilerType element_type (getASTContext(), array_eletype->getCanonicalTypeUnqualified());
-
- // TODO: the real stride will be >= this value.. find the real one!
- if (stride)
- *stride = element_type.GetByteSize(nullptr);
-
- return element_type;
-
- }
- return CompilerType();
-}
+ClangASTContext::GetArrayElementType(lldb::opaque_compiler_type_t type,
+ uint64_t *stride) {
+ if (type) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
-CompilerType
-ClangASTContext::GetArrayType (lldb::opaque_compiler_type_t type, uint64_t size)
-{
- if (type)
- {
- clang::QualType qual_type(GetCanonicalQualType(type));
- if (clang::ASTContext *ast_ctx = getASTContext())
- {
- if (size != 0)
- return CompilerType (ast_ctx, ast_ctx->getConstantArrayType(qual_type, llvm::APInt(64, size), clang::ArrayType::ArraySizeModifier::Normal, 0));
- else
- return CompilerType (ast_ctx, ast_ctx->getIncompleteArrayType(qual_type, clang::ArrayType::ArraySizeModifier::Normal, 0));
- }
- }
-
- return CompilerType();
-}
+ const clang::Type *array_eletype =
+ qual_type.getTypePtr()->getArrayElementTypeNoTypeQual();
-CompilerType
-ClangASTContext::GetCanonicalType (lldb::opaque_compiler_type_t type)
-{
- if (type)
- return CompilerType (getASTContext(), GetCanonicalQualType(type));
- return CompilerType();
+ if (!array_eletype)
+ return CompilerType();
+
+ CompilerType element_type(getASTContext(),
+ array_eletype->getCanonicalTypeUnqualified());
+
+ // TODO: the real stride will be >= this value.. find the real one!
+ if (stride)
+ *stride = element_type.GetByteSize(nullptr);
+
+ return element_type;
+ }
+ return CompilerType();
}
-static clang::QualType
-GetFullyUnqualifiedType_Impl (clang::ASTContext *ast, clang::QualType qual_type)
-{
- if (qual_type->isPointerType())
- qual_type = ast->getPointerType(GetFullyUnqualifiedType_Impl(ast, qual_type->getPointeeType()));
- else
- qual_type = qual_type.getUnqualifiedType();
- qual_type.removeLocalConst();
- qual_type.removeLocalRestrict();
- qual_type.removeLocalVolatile();
- return qual_type;
+CompilerType ClangASTContext::GetArrayType(lldb::opaque_compiler_type_t type,
+ uint64_t size) {
+ if (type) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ if (clang::ASTContext *ast_ctx = getASTContext()) {
+ if (size != 0)
+ return CompilerType(
+ ast_ctx, ast_ctx->getConstantArrayType(
+ qual_type, llvm::APInt(64, size),
+ clang::ArrayType::ArraySizeModifier::Normal, 0));
+ else
+ return CompilerType(
+ ast_ctx,
+ ast_ctx->getIncompleteArrayType(
+ qual_type, clang::ArrayType::ArraySizeModifier::Normal, 0));
+ }
+ }
+
+ return CompilerType();
}
CompilerType
-ClangASTContext::GetFullyUnqualifiedType (lldb::opaque_compiler_type_t type)
-{
- if (type)
- return CompilerType(getASTContext(), GetFullyUnqualifiedType_Impl(getASTContext(), GetQualType(type)));
- return CompilerType();
+ClangASTContext::GetCanonicalType(lldb::opaque_compiler_type_t type) {
+ if (type)
+ return CompilerType(getASTContext(), GetCanonicalQualType(type));
+ return CompilerType();
}
-
-int
-ClangASTContext::GetFunctionArgumentCount (lldb::opaque_compiler_type_t type)
-{
- if (type)
- {
- const clang::FunctionProtoType* func = llvm::dyn_cast<clang::FunctionProtoType>(GetCanonicalQualType(type));
- if (func)
- return func->getNumParams();
- }
- return -1;
+static clang::QualType GetFullyUnqualifiedType_Impl(clang::ASTContext *ast,
+ clang::QualType qual_type) {
+ if (qual_type->isPointerType())
+ qual_type = ast->getPointerType(
+ GetFullyUnqualifiedType_Impl(ast, qual_type->getPointeeType()));
+ else
+ qual_type = qual_type.getUnqualifiedType();
+ qual_type.removeLocalConst();
+ qual_type.removeLocalRestrict();
+ qual_type.removeLocalVolatile();
+ return qual_type;
}
CompilerType
-ClangASTContext::GetFunctionArgumentTypeAtIndex (lldb::opaque_compiler_type_t type, size_t idx)
-{
- if (type)
- {
- const clang::FunctionProtoType* func = llvm::dyn_cast<clang::FunctionProtoType>(GetQualType(type));
- if (func)
- {
- const uint32_t num_args = func->getNumParams();
- if (idx < num_args)
- return CompilerType(getASTContext(), func->getParamType(idx));
- }
- }
- return CompilerType();
+ClangASTContext::GetFullyUnqualifiedType(lldb::opaque_compiler_type_t type) {
+ if (type)
+ return CompilerType(
+ getASTContext(),
+ GetFullyUnqualifiedType_Impl(getASTContext(), GetQualType(type)));
+ return CompilerType();
+}
+
+int ClangASTContext::GetFunctionArgumentCount(
+ lldb::opaque_compiler_type_t type) {
+ if (type) {
+ const clang::FunctionProtoType *func =
+ llvm::dyn_cast<clang::FunctionProtoType>(GetCanonicalQualType(type));
+ if (func)
+ return func->getNumParams();
+ }
+ return -1;
+}
+
+CompilerType ClangASTContext::GetFunctionArgumentTypeAtIndex(
+ lldb::opaque_compiler_type_t type, size_t idx) {
+ if (type) {
+ const clang::FunctionProtoType *func =
+ llvm::dyn_cast<clang::FunctionProtoType>(GetQualType(type));
+ if (func) {
+ const uint32_t num_args = func->getNumParams();
+ if (idx < num_args)
+ return CompilerType(getASTContext(), func->getParamType(idx));
+ }
+ }
+ return CompilerType();
}
CompilerType
-ClangASTContext::GetFunctionReturnType (lldb::opaque_compiler_type_t type)
-{
- if (type)
- {
- clang::QualType qual_type(GetQualType(type));
- const clang::FunctionProtoType* func = llvm::dyn_cast<clang::FunctionProtoType>(qual_type.getTypePtr());
- if (func)
- return CompilerType(getASTContext(), func->getReturnType());
- }
- return CompilerType();
+ClangASTContext::GetFunctionReturnType(lldb::opaque_compiler_type_t type) {
+ if (type) {
+ clang::QualType qual_type(GetQualType(type));
+ const clang::FunctionProtoType *func =
+ llvm::dyn_cast<clang::FunctionProtoType>(qual_type.getTypePtr());
+ if (func)
+ return CompilerType(getASTContext(), func->getReturnType());
+ }
+ return CompilerType();
}
size_t
-ClangASTContext::GetNumMemberFunctions (lldb::opaque_compiler_type_t type)
-{
- size_t num_functions = 0;
- if (type)
- {
- clang::QualType qual_type(GetCanonicalQualType(type));
- switch (qual_type->getTypeClass()) {
- case clang::Type::Record:
- if (GetCompleteQualType (getASTContext(), qual_type))
- {
- const clang::RecordType *record_type = llvm::cast<clang::RecordType>(qual_type.getTypePtr());
- const clang::RecordDecl *record_decl = record_type->getDecl();
- assert(record_decl);
- const clang::CXXRecordDecl *cxx_record_decl = llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
- if (cxx_record_decl)
- num_functions = std::distance(cxx_record_decl->method_begin(), cxx_record_decl->method_end());
- }
- break;
-
- case clang::Type::ObjCObjectPointer:
- if (GetCompleteType(type))
- {
- const clang::ObjCObjectPointerType *objc_class_type = qual_type->getAsObjCInterfacePointerType();
- if (objc_class_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterfaceDecl();
- if (class_interface_decl)
- num_functions = std::distance(class_interface_decl->meth_begin(), class_interface_decl->meth_end());
- }
- }
- break;
-
- case clang::Type::ObjCObject:
- case clang::Type::ObjCInterface:
- if (GetCompleteType(type))
- {
- const clang::ObjCObjectType *objc_class_type = llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
- if (objc_class_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
- if (class_interface_decl)
- num_functions = std::distance(class_interface_decl->meth_begin(), class_interface_decl->meth_end());
- }
- }
- break;
-
-
- case clang::Type::Typedef:
- return CompilerType (getASTContext(), llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType()).GetNumMemberFunctions();
-
- case clang::Type::Auto:
- return CompilerType (getASTContext(), llvm::cast<clang::AutoType>(qual_type)->getDeducedType()).GetNumMemberFunctions();
-
- case clang::Type::Elaborated:
- return CompilerType (getASTContext(), llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType()).GetNumMemberFunctions();
-
- case clang::Type::Paren:
- return CompilerType (getASTContext(), llvm::cast<clang::ParenType>(qual_type)->desugar()).GetNumMemberFunctions();
-
- default:
- break;
+ClangASTContext::GetNumMemberFunctions(lldb::opaque_compiler_type_t type) {
+ size_t num_functions = 0;
+ if (type) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ switch (qual_type->getTypeClass()) {
+ case clang::Type::Record:
+ if (GetCompleteQualType(getASTContext(), qual_type)) {
+ const clang::RecordType *record_type =
+ llvm::cast<clang::RecordType>(qual_type.getTypePtr());
+ const clang::RecordDecl *record_decl = record_type->getDecl();
+ assert(record_decl);
+ const clang::CXXRecordDecl *cxx_record_decl =
+ llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
+ if (cxx_record_decl)
+ num_functions = std::distance(cxx_record_decl->method_begin(),
+ cxx_record_decl->method_end());
+ }
+ break;
+
+ case clang::Type::ObjCObjectPointer:
+ if (GetCompleteType(type)) {
+ const clang::ObjCObjectPointerType *objc_class_type =
+ qual_type->getAsObjCInterfacePointerType();
+ if (objc_class_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterfaceDecl();
+ if (class_interface_decl)
+ num_functions = std::distance(class_interface_decl->meth_begin(),
+ class_interface_decl->meth_end());
+ }
+ }
+ break;
+
+ case clang::Type::ObjCObject:
+ case clang::Type::ObjCInterface:
+ if (GetCompleteType(type)) {
+ const clang::ObjCObjectType *objc_class_type =
+ llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
+ if (objc_class_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterface();
+ if (class_interface_decl)
+ num_functions = std::distance(class_interface_decl->meth_begin(),
+ class_interface_decl->meth_end());
}
+ }
+ break;
+
+ case clang::Type::Typedef:
+ return CompilerType(getASTContext(),
+ llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType())
+ .GetNumMemberFunctions();
+
+ case clang::Type::Auto:
+ return CompilerType(
+ getASTContext(),
+ llvm::cast<clang::AutoType>(qual_type)->getDeducedType())
+ .GetNumMemberFunctions();
+
+ case clang::Type::Elaborated:
+ return CompilerType(
+ getASTContext(),
+ llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType())
+ .GetNumMemberFunctions();
+
+ case clang::Type::Paren:
+ return CompilerType(getASTContext(),
+ llvm::cast<clang::ParenType>(qual_type)->desugar())
+ .GetNumMemberFunctions();
+
+ default:
+ break;
}
- return num_functions;
+ }
+ return num_functions;
}
TypeMemberFunctionImpl
-ClangASTContext::GetMemberFunctionAtIndex (lldb::opaque_compiler_type_t type, size_t idx)
-{
- std::string name;
- MemberFunctionKind kind(MemberFunctionKind::eMemberFunctionKindUnknown);
- CompilerType clang_type;
- CompilerDecl clang_decl;
- if (type)
- {
- clang::QualType qual_type(GetCanonicalQualType(type));
- switch (qual_type->getTypeClass()) {
- case clang::Type::Record:
- if (GetCompleteQualType (getASTContext(), qual_type))
- {
- const clang::RecordType *record_type = llvm::cast<clang::RecordType>(qual_type.getTypePtr());
- const clang::RecordDecl *record_decl = record_type->getDecl();
- assert(record_decl);
- const clang::CXXRecordDecl *cxx_record_decl = llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
- if (cxx_record_decl)
- {
- auto method_iter = cxx_record_decl->method_begin();
- auto method_end = cxx_record_decl->method_end();
- if (idx < static_cast<size_t>(std::distance(method_iter, method_end)))
- {
- std::advance(method_iter, idx);
- clang::CXXMethodDecl *cxx_method_decl = method_iter->getCanonicalDecl();
- if (cxx_method_decl)
- {
- name = cxx_method_decl->getDeclName().getAsString();
- if (cxx_method_decl->isStatic())
- kind = lldb::eMemberFunctionKindStaticMethod;
- else if (llvm::isa<clang::CXXConstructorDecl>(cxx_method_decl))
- kind = lldb::eMemberFunctionKindConstructor;
- else if (llvm::isa<clang::CXXDestructorDecl>(cxx_method_decl))
- kind = lldb::eMemberFunctionKindDestructor;
- else
- kind = lldb::eMemberFunctionKindInstanceMethod;
- clang_type = CompilerType(this, cxx_method_decl->getType().getAsOpaquePtr());
- clang_decl = CompilerDecl(this, cxx_method_decl);
- }
- }
- }
- }
- break;
-
- case clang::Type::ObjCObjectPointer:
- if (GetCompleteType(type))
- {
- const clang::ObjCObjectPointerType *objc_class_type = qual_type->getAsObjCInterfacePointerType();
- if (objc_class_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterfaceDecl();
- if (class_interface_decl)
- {
- auto method_iter = class_interface_decl->meth_begin();
- auto method_end = class_interface_decl->meth_end();
- if (idx < static_cast<size_t>(std::distance(method_iter, method_end)))
- {
- std::advance(method_iter, idx);
- clang::ObjCMethodDecl *objc_method_decl = method_iter->getCanonicalDecl();
- if (objc_method_decl)
- {
- clang_decl = CompilerDecl(this, objc_method_decl);
- name = objc_method_decl->getSelector().getAsString();
- if (objc_method_decl->isClassMethod())
- kind = lldb::eMemberFunctionKindStaticMethod;
- else
- kind = lldb::eMemberFunctionKindInstanceMethod;
- }
- }
- }
- }
- }
- break;
-
- case clang::Type::ObjCObject:
- case clang::Type::ObjCInterface:
- if (GetCompleteType(type))
- {
- const clang::ObjCObjectType *objc_class_type = llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
- if (objc_class_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
- if (class_interface_decl)
- {
- auto method_iter = class_interface_decl->meth_begin();
- auto method_end = class_interface_decl->meth_end();
- if (idx < static_cast<size_t>(std::distance(method_iter, method_end)))
- {
- std::advance(method_iter, idx);
- clang::ObjCMethodDecl *objc_method_decl = method_iter->getCanonicalDecl();
- if (objc_method_decl)
- {
- clang_decl = CompilerDecl(this, objc_method_decl);
- name = objc_method_decl->getSelector().getAsString();
- if (objc_method_decl->isClassMethod())
- kind = lldb::eMemberFunctionKindStaticMethod;
- else
- kind = lldb::eMemberFunctionKindInstanceMethod;
- }
- }
- }
- }
- }
- break;
-
- case clang::Type::Typedef:
- return GetMemberFunctionAtIndex(llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(), idx);
-
- case clang::Type::Auto:
- return GetMemberFunctionAtIndex(llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr(), idx);
-
- case clang::Type::Elaborated:
- return GetMemberFunctionAtIndex(llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr(), idx);
-
- case clang::Type::Paren:
- return GetMemberFunctionAtIndex(llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(), idx);
-
- default:
- break;
+ClangASTContext::GetMemberFunctionAtIndex(lldb::opaque_compiler_type_t type,
+ size_t idx) {
+ std::string name;
+ MemberFunctionKind kind(MemberFunctionKind::eMemberFunctionKindUnknown);
+ CompilerType clang_type;
+ CompilerDecl clang_decl;
+ if (type) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ switch (qual_type->getTypeClass()) {
+ case clang::Type::Record:
+ if (GetCompleteQualType(getASTContext(), qual_type)) {
+ const clang::RecordType *record_type =
+ llvm::cast<clang::RecordType>(qual_type.getTypePtr());
+ const clang::RecordDecl *record_decl = record_type->getDecl();
+ assert(record_decl);
+ const clang::CXXRecordDecl *cxx_record_decl =
+ llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
+ if (cxx_record_decl) {
+ auto method_iter = cxx_record_decl->method_begin();
+ auto method_end = cxx_record_decl->method_end();
+ if (idx <
+ static_cast<size_t>(std::distance(method_iter, method_end))) {
+ std::advance(method_iter, idx);
+ clang::CXXMethodDecl *cxx_method_decl =
+ method_iter->getCanonicalDecl();
+ if (cxx_method_decl) {
+ name = cxx_method_decl->getDeclName().getAsString();
+ if (cxx_method_decl->isStatic())
+ kind = lldb::eMemberFunctionKindStaticMethod;
+ else if (llvm::isa<clang::CXXConstructorDecl>(cxx_method_decl))
+ kind = lldb::eMemberFunctionKindConstructor;
+ else if (llvm::isa<clang::CXXDestructorDecl>(cxx_method_decl))
+ kind = lldb::eMemberFunctionKindDestructor;
+ else
+ kind = lldb::eMemberFunctionKindInstanceMethod;
+ clang_type = CompilerType(
+ this, cxx_method_decl->getType().getAsOpaquePtr());
+ clang_decl = CompilerDecl(this, cxx_method_decl);
+ }
+ }
}
+ }
+ break;
+
+ case clang::Type::ObjCObjectPointer:
+ if (GetCompleteType(type)) {
+ const clang::ObjCObjectPointerType *objc_class_type =
+ qual_type->getAsObjCInterfacePointerType();
+ if (objc_class_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterfaceDecl();
+ if (class_interface_decl) {
+ auto method_iter = class_interface_decl->meth_begin();
+ auto method_end = class_interface_decl->meth_end();
+ if (idx <
+ static_cast<size_t>(std::distance(method_iter, method_end))) {
+ std::advance(method_iter, idx);
+ clang::ObjCMethodDecl *objc_method_decl =
+ method_iter->getCanonicalDecl();
+ if (objc_method_decl) {
+ clang_decl = CompilerDecl(this, objc_method_decl);
+ name = objc_method_decl->getSelector().getAsString();
+ if (objc_method_decl->isClassMethod())
+ kind = lldb::eMemberFunctionKindStaticMethod;
+ else
+ kind = lldb::eMemberFunctionKindInstanceMethod;
+ }
+ }
+ }
+ }
+ }
+ break;
+
+ case clang::Type::ObjCObject:
+ case clang::Type::ObjCInterface:
+ if (GetCompleteType(type)) {
+ const clang::ObjCObjectType *objc_class_type =
+ llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
+ if (objc_class_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterface();
+ if (class_interface_decl) {
+ auto method_iter = class_interface_decl->meth_begin();
+ auto method_end = class_interface_decl->meth_end();
+ if (idx <
+ static_cast<size_t>(std::distance(method_iter, method_end))) {
+ std::advance(method_iter, idx);
+ clang::ObjCMethodDecl *objc_method_decl =
+ method_iter->getCanonicalDecl();
+ if (objc_method_decl) {
+ clang_decl = CompilerDecl(this, objc_method_decl);
+ name = objc_method_decl->getSelector().getAsString();
+ if (objc_method_decl->isClassMethod())
+ kind = lldb::eMemberFunctionKindStaticMethod;
+ else
+ kind = lldb::eMemberFunctionKindInstanceMethod;
+ }
+ }
+ }
+ }
+ }
+ break;
+
+ case clang::Type::Typedef:
+ return GetMemberFunctionAtIndex(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr(),
+ idx);
+
+ case clang::Type::Auto:
+ return GetMemberFunctionAtIndex(llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr(),
+ idx);
+
+ case clang::Type::Elaborated:
+ return GetMemberFunctionAtIndex(
+ llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr(),
+ idx);
+
+ case clang::Type::Paren:
+ return GetMemberFunctionAtIndex(
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(),
+ idx);
+
+ default:
+ break;
}
-
- if (kind == eMemberFunctionKindUnknown)
- return TypeMemberFunctionImpl();
- else
- return TypeMemberFunctionImpl(clang_type, clang_decl, name, kind);
+ }
+
+ if (kind == eMemberFunctionKindUnknown)
+ return TypeMemberFunctionImpl();
+ else
+ return TypeMemberFunctionImpl(clang_type, clang_decl, name, kind);
}
CompilerType
-ClangASTContext::GetNonReferenceType (lldb::opaque_compiler_type_t type)
-{
- if (type)
- return CompilerType(getASTContext(), GetQualType(type).getNonReferenceType());
- return CompilerType();
+ClangASTContext::GetNonReferenceType(lldb::opaque_compiler_type_t type) {
+ if (type)
+ return CompilerType(getASTContext(),
+ GetQualType(type).getNonReferenceType());
+ return CompilerType();
+}
+
+CompilerType ClangASTContext::CreateTypedefType(
+ const CompilerType &type, const char *typedef_name,
+ const CompilerDeclContext &compiler_decl_ctx) {
+ if (type && typedef_name && typedef_name[0]) {
+ ClangASTContext *ast =
+ llvm::dyn_cast<ClangASTContext>(type.GetTypeSystem());
+ if (!ast)
+ return CompilerType();
+ clang::ASTContext *clang_ast = ast->getASTContext();
+ clang::QualType qual_type(ClangUtil::GetQualType(type));
+
+ clang::DeclContext *decl_ctx =
+ ClangASTContext::DeclContextGetAsDeclContext(compiler_decl_ctx);
+ if (decl_ctx == nullptr)
+ decl_ctx = ast->getASTContext()->getTranslationUnitDecl();
+
+ clang::TypedefDecl *decl = clang::TypedefDecl::Create(
+ *clang_ast, decl_ctx, clang::SourceLocation(), clang::SourceLocation(),
+ &clang_ast->Idents.get(typedef_name),
+ clang_ast->getTrivialTypeSourceInfo(qual_type));
+
+ decl->setAccess(clang::AS_public); // TODO respect proper access specifier
+
+ // Get a uniqued clang::QualType for the typedef decl type
+ return CompilerType(clang_ast, clang_ast->getTypedefType(decl));
+ }
+ return CompilerType();
}
CompilerType
-ClangASTContext::CreateTypedefType (const CompilerType& type,
- const char *typedef_name,
- const CompilerDeclContext &compiler_decl_ctx)
-{
- if (type && typedef_name && typedef_name[0])
- {
- ClangASTContext *ast = llvm::dyn_cast<ClangASTContext>(type.GetTypeSystem());
- if (!ast)
- return CompilerType();
- clang::ASTContext* clang_ast = ast->getASTContext();
- clang::QualType qual_type(ClangUtil::GetQualType(type));
-
- clang::DeclContext *decl_ctx = ClangASTContext::DeclContextGetAsDeclContext(compiler_decl_ctx);
- if (decl_ctx == nullptr)
- decl_ctx = ast->getASTContext()->getTranslationUnitDecl();
-
- clang::TypedefDecl *decl = clang::TypedefDecl::Create (*clang_ast,
- decl_ctx,
- clang::SourceLocation(),
- clang::SourceLocation(),
- &clang_ast->Idents.get(typedef_name),
- clang_ast->getTrivialTypeSourceInfo(qual_type));
-
- decl->setAccess(clang::AS_public); // TODO respect proper access specifier
-
- // Get a uniqued clang::QualType for the typedef decl type
- return CompilerType (clang_ast, clang_ast->getTypedefType (decl));
- }
- return CompilerType();
-
+ClangASTContext::GetPointeeType(lldb::opaque_compiler_type_t type) {
+ if (type) {
+ clang::QualType qual_type(GetQualType(type));
+ return CompilerType(getASTContext(),
+ qual_type.getTypePtr()->getPointeeType());
+ }
+ return CompilerType();
}
CompilerType
-ClangASTContext::GetPointeeType (lldb::opaque_compiler_type_t type)
-{
- if (type)
- {
- clang::QualType qual_type(GetQualType(type));
- return CompilerType (getASTContext(), qual_type.getTypePtr()->getPointeeType());
+ClangASTContext::GetPointerType(lldb::opaque_compiler_type_t type) {
+ if (type) {
+ clang::QualType qual_type(GetQualType(type));
+
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::ObjCObject:
+ case clang::Type::ObjCInterface:
+ return CompilerType(getASTContext(),
+ getASTContext()->getObjCObjectPointerType(qual_type));
+
+ default:
+ return CompilerType(getASTContext(),
+ getASTContext()->getPointerType(qual_type));
}
- return CompilerType();
+ }
+ return CompilerType();
}
CompilerType
-ClangASTContext::GetPointerType (lldb::opaque_compiler_type_t type)
-{
- if (type)
- {
- clang::QualType qual_type (GetQualType(type));
-
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::ObjCObject:
- case clang::Type::ObjCInterface:
- return CompilerType(getASTContext(), getASTContext()->getObjCObjectPointerType(qual_type));
-
- default:
- return CompilerType(getASTContext(), getASTContext()->getPointerType(qual_type));
- }
- }
+ClangASTContext::GetLValueReferenceType(lldb::opaque_compiler_type_t type) {
+ if (type)
+ return CompilerType(this, getASTContext()
+ ->getLValueReferenceType(GetQualType(type))
+ .getAsOpaquePtr());
+ else
return CompilerType();
}
-
CompilerType
-ClangASTContext::GetLValueReferenceType (lldb::opaque_compiler_type_t type)
-{
- if (type)
- return CompilerType(this, getASTContext()->getLValueReferenceType(GetQualType(type)).getAsOpaquePtr());
- else
- return CompilerType();
+ClangASTContext::GetRValueReferenceType(lldb::opaque_compiler_type_t type) {
+ if (type)
+ return CompilerType(this, getASTContext()
+ ->getRValueReferenceType(GetQualType(type))
+ .getAsOpaquePtr());
+ else
+ return CompilerType();
}
CompilerType
-ClangASTContext::GetRValueReferenceType (lldb::opaque_compiler_type_t type)
-{
- if (type)
- return CompilerType(this, getASTContext()->getRValueReferenceType(GetQualType(type)).getAsOpaquePtr());
- else
- return CompilerType();
+ClangASTContext::AddConstModifier(lldb::opaque_compiler_type_t type) {
+ if (type) {
+ clang::QualType result(GetQualType(type));
+ result.addConst();
+ return CompilerType(this, result.getAsOpaquePtr());
+ }
+ return CompilerType();
}
CompilerType
-ClangASTContext::AddConstModifier (lldb::opaque_compiler_type_t type)
-{
- if (type)
- {
- clang::QualType result(GetQualType(type));
- result.addConst();
- return CompilerType (this, result.getAsOpaquePtr());
- }
- return CompilerType();
+ClangASTContext::AddVolatileModifier(lldb::opaque_compiler_type_t type) {
+ if (type) {
+ clang::QualType result(GetQualType(type));
+ result.addVolatile();
+ return CompilerType(this, result.getAsOpaquePtr());
+ }
+ return CompilerType();
}
CompilerType
-ClangASTContext::AddVolatileModifier (lldb::opaque_compiler_type_t type)
-{
- if (type)
- {
- clang::QualType result(GetQualType(type));
- result.addVolatile();
- return CompilerType (this, result.getAsOpaquePtr());
- }
- return CompilerType();
-
+ClangASTContext::AddRestrictModifier(lldb::opaque_compiler_type_t type) {
+ if (type) {
+ clang::QualType result(GetQualType(type));
+ result.addRestrict();
+ return CompilerType(this, result.getAsOpaquePtr());
+ }
+ return CompilerType();
}
CompilerType
-ClangASTContext::AddRestrictModifier (lldb::opaque_compiler_type_t type)
-{
- if (type)
- {
- clang::QualType result(GetQualType(type));
- result.addRestrict();
- return CompilerType (this, result.getAsOpaquePtr());
- }
- return CompilerType();
-
-}
+ClangASTContext::CreateTypedef(lldb::opaque_compiler_type_t type,
+ const char *typedef_name,
+ const CompilerDeclContext &compiler_decl_ctx) {
+ if (type) {
+ clang::ASTContext *clang_ast = getASTContext();
+ clang::QualType qual_type(GetQualType(type));
-CompilerType
-ClangASTContext::CreateTypedef (lldb::opaque_compiler_type_t type, const char *typedef_name, const CompilerDeclContext &compiler_decl_ctx)
-{
- if (type)
- {
- clang::ASTContext* clang_ast = getASTContext();
- clang::QualType qual_type (GetQualType(type));
-
- clang::DeclContext *decl_ctx = ClangASTContext::DeclContextGetAsDeclContext(compiler_decl_ctx);
- if (decl_ctx == nullptr)
- decl_ctx = getASTContext()->getTranslationUnitDecl();
-
- clang::TypedefDecl *decl = clang::TypedefDecl::Create (*clang_ast,
- decl_ctx,
- clang::SourceLocation(),
- clang::SourceLocation(),
- &clang_ast->Idents.get(typedef_name),
- clang_ast->getTrivialTypeSourceInfo(qual_type));
-
- clang::TagDecl *tdecl = nullptr;
- if (!qual_type.isNull())
- {
- if (const clang::RecordType *rt = qual_type->getAs<clang::RecordType>())
- tdecl = rt->getDecl();
- if (const clang::EnumType *et = qual_type->getAs<clang::EnumType>())
- tdecl = et->getDecl();
- }
+ clang::DeclContext *decl_ctx =
+ ClangASTContext::DeclContextGetAsDeclContext(compiler_decl_ctx);
+ if (decl_ctx == nullptr)
+ decl_ctx = getASTContext()->getTranslationUnitDecl();
- // Check whether this declaration is an anonymous struct, union, or enum, hidden behind a typedef. If so, we
- // try to check whether we have a typedef tag to attach to the original record declaration
- if (tdecl && !tdecl->getIdentifier() && !tdecl->getTypedefNameForAnonDecl())
- tdecl->setTypedefNameForAnonDecl(decl);
+ clang::TypedefDecl *decl = clang::TypedefDecl::Create(
+ *clang_ast, decl_ctx, clang::SourceLocation(), clang::SourceLocation(),
+ &clang_ast->Idents.get(typedef_name),
+ clang_ast->getTrivialTypeSourceInfo(qual_type));
- decl->setAccess(clang::AS_public); // TODO respect proper access specifier
+ clang::TagDecl *tdecl = nullptr;
+ if (!qual_type.isNull()) {
+ if (const clang::RecordType *rt = qual_type->getAs<clang::RecordType>())
+ tdecl = rt->getDecl();
+ if (const clang::EnumType *et = qual_type->getAs<clang::EnumType>())
+ tdecl = et->getDecl();
+ }
- // Get a uniqued clang::QualType for the typedef decl type
- return CompilerType (this, clang_ast->getTypedefType (decl).getAsOpaquePtr());
+ // Check whether this declaration is an anonymous struct, union, or enum,
+ // hidden behind a typedef. If so, we
+ // try to check whether we have a typedef tag to attach to the original
+ // record declaration
+ if (tdecl && !tdecl->getIdentifier() && !tdecl->getTypedefNameForAnonDecl())
+ tdecl->setTypedefNameForAnonDecl(decl);
- }
- return CompilerType();
+ decl->setAccess(clang::AS_public); // TODO respect proper access specifier
+ // Get a uniqued clang::QualType for the typedef decl type
+ return CompilerType(this, clang_ast->getTypedefType(decl).getAsOpaquePtr());
+ }
+ return CompilerType();
}
CompilerType
-ClangASTContext::GetTypedefedType (lldb::opaque_compiler_type_t type)
-{
- if (type)
- {
- const clang::TypedefType *typedef_type = llvm::dyn_cast<clang::TypedefType>(GetQualType(type));
- if (typedef_type)
- return CompilerType (getASTContext(), typedef_type->getDecl()->getUnderlyingType());
- }
- return CompilerType();
+ClangASTContext::GetTypedefedType(lldb::opaque_compiler_type_t type) {
+ if (type) {
+ const clang::TypedefType *typedef_type =
+ llvm::dyn_cast<clang::TypedefType>(GetQualType(type));
+ if (typedef_type)
+ return CompilerType(getASTContext(),
+ typedef_type->getDecl()->getUnderlyingType());
+ }
+ return CompilerType();
}
-
//----------------------------------------------------------------------
// Create related types using the current type's AST
//----------------------------------------------------------------------
-CompilerType
-ClangASTContext::GetBasicTypeFromAST (lldb::BasicType basic_type)
-{
- return ClangASTContext::GetBasicType(getASTContext(), basic_type);
+CompilerType ClangASTContext::GetBasicTypeFromAST(lldb::BasicType basic_type) {
+ return ClangASTContext::GetBasicType(getASTContext(), basic_type);
}
//----------------------------------------------------------------------
// Exploring the type
//----------------------------------------------------------------------
-uint64_t
-ClangASTContext::GetBitSize (lldb::opaque_compiler_type_t type, ExecutionContextScope *exe_scope)
-{
- if (GetCompleteType (type))
- {
- clang::QualType qual_type(GetCanonicalQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Record:
- if (GetCompleteType(type))
- return getASTContext()->getTypeSize(qual_type);
- else
- return 0;
- break;
-
- case clang::Type::ObjCInterface:
- case clang::Type::ObjCObject:
- {
- ExecutionContext exe_ctx (exe_scope);
- Process *process = exe_ctx.GetProcessPtr();
- if (process)
- {
- ObjCLanguageRuntime *objc_runtime = process->GetObjCLanguageRuntime();
- if (objc_runtime)
- {
- uint64_t bit_size = 0;
- if (objc_runtime->GetTypeBitSize(CompilerType(getASTContext(), qual_type), bit_size))
- return bit_size;
- }
- }
- else
- {
- static bool g_printed = false;
- if (!g_printed)
- {
- StreamString s;
- DumpTypeDescription(type, &s);
-
- llvm::outs() << "warning: trying to determine the size of type ";
- llvm::outs() << s.GetString() << "\n";
- llvm::outs() << "without a valid ExecutionContext. this is not reliable. please file a bug against LLDB.\n";
- llvm::outs() << "backtrace:\n";
- llvm::sys::PrintStackTrace(llvm::outs());
- llvm::outs() << "\n";
- g_printed = true;
- }
- }
- }
- LLVM_FALLTHROUGH;
- default:
- const uint32_t bit_size = getASTContext()->getTypeSize (qual_type);
- if (bit_size == 0)
- {
- if (qual_type->isIncompleteArrayType())
- return getASTContext()->getTypeSize (qual_type->getArrayElementTypeNoTypeQual()->getCanonicalTypeUnqualified());
- }
- if (qual_type->isObjCObjectOrInterfaceType())
- return bit_size + getASTContext()->getTypeSize(getASTContext()->ObjCBuiltinClassTy);
- return bit_size;
+uint64_t ClangASTContext::GetBitSize(lldb::opaque_compiler_type_t type,
+ ExecutionContextScope *exe_scope) {
+ if (GetCompleteType(type)) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Record:
+ if (GetCompleteType(type))
+ return getASTContext()->getTypeSize(qual_type);
+ else
+ return 0;
+ break;
+
+ case clang::Type::ObjCInterface:
+ case clang::Type::ObjCObject: {
+ ExecutionContext exe_ctx(exe_scope);
+ Process *process = exe_ctx.GetProcessPtr();
+ if (process) {
+ ObjCLanguageRuntime *objc_runtime = process->GetObjCLanguageRuntime();
+ if (objc_runtime) {
+ uint64_t bit_size = 0;
+ if (objc_runtime->GetTypeBitSize(
+ CompilerType(getASTContext(), qual_type), bit_size))
+ return bit_size;
+ }
+ } else {
+ static bool g_printed = false;
+ if (!g_printed) {
+ StreamString s;
+ DumpTypeDescription(type, &s);
+
+ llvm::outs() << "warning: trying to determine the size of type ";
+ llvm::outs() << s.GetString() << "\n";
+ llvm::outs() << "without a valid ExecutionContext. this is not "
+ "reliable. please file a bug against LLDB.\n";
+ llvm::outs() << "backtrace:\n";
+ llvm::sys::PrintStackTrace(llvm::outs());
+ llvm::outs() << "\n";
+ g_printed = true;
}
+ }
}
- return 0;
-}
+ LLVM_FALLTHROUGH;
+ default:
+ const uint32_t bit_size = getASTContext()->getTypeSize(qual_type);
+ if (bit_size == 0) {
+ if (qual_type->isIncompleteArrayType())
+ return getASTContext()->getTypeSize(
+ qual_type->getArrayElementTypeNoTypeQual()
+ ->getCanonicalTypeUnqualified());
+ }
+ if (qual_type->isObjCObjectOrInterfaceType())
+ return bit_size +
+ getASTContext()->getTypeSize(
+ getASTContext()->ObjCBuiltinClassTy);
+ return bit_size;
+ }
+ }
+ return 0;
+}
+
+size_t ClangASTContext::GetTypeBitAlign(lldb::opaque_compiler_type_t type) {
+ if (GetCompleteType(type))
+ return getASTContext()->getTypeAlign(GetQualType(type));
+ return 0;
+}
+
+lldb::Encoding ClangASTContext::GetEncoding(lldb::opaque_compiler_type_t type,
+ uint64_t &count) {
+ if (!type)
+ return lldb::eEncodingInvalid;
-size_t
-ClangASTContext::GetTypeBitAlign (lldb::opaque_compiler_type_t type)
-{
- if (GetCompleteType(type))
- return getASTContext()->getTypeAlign(GetQualType(type));
- return 0;
+ count = 1;
+ clang::QualType qual_type(GetCanonicalQualType(type));
+
+ switch (qual_type->getTypeClass()) {
+ case clang::Type::UnaryTransform:
+ break;
+
+ case clang::Type::FunctionNoProto:
+ case clang::Type::FunctionProto:
+ break;
+
+ case clang::Type::IncompleteArray:
+ case clang::Type::VariableArray:
+ break;
+
+ case clang::Type::ConstantArray:
+ break;
+
+ case clang::Type::ExtVector:
+ case clang::Type::Vector:
+ // TODO: Set this to more than one???
+ break;
+
+ case clang::Type::Builtin:
+ switch (llvm::cast<clang::BuiltinType>(qual_type)->getKind()) {
+ case clang::BuiltinType::Void:
+ break;
+
+ case clang::BuiltinType::Bool:
+ case clang::BuiltinType::Char_S:
+ case clang::BuiltinType::SChar:
+ case clang::BuiltinType::WChar_S:
+ case clang::BuiltinType::Char16:
+ case clang::BuiltinType::Char32:
+ case clang::BuiltinType::Short:
+ case clang::BuiltinType::Int:
+ case clang::BuiltinType::Long:
+ case clang::BuiltinType::LongLong:
+ case clang::BuiltinType::Int128:
+ return lldb::eEncodingSint;
+
+ case clang::BuiltinType::Char_U:
+ case clang::BuiltinType::UChar:
+ case clang::BuiltinType::WChar_U:
+ case clang::BuiltinType::UShort:
+ case clang::BuiltinType::UInt:
+ case clang::BuiltinType::ULong:
+ case clang::BuiltinType::ULongLong:
+ case clang::BuiltinType::UInt128:
+ return lldb::eEncodingUint;
+
+ case clang::BuiltinType::Half:
+ case clang::BuiltinType::Float:
+ case clang::BuiltinType::Float128:
+ case clang::BuiltinType::Double:
+ case clang::BuiltinType::LongDouble:
+ return lldb::eEncodingIEEE754;
+
+ case clang::BuiltinType::ObjCClass:
+ case clang::BuiltinType::ObjCId:
+ case clang::BuiltinType::ObjCSel:
+ return lldb::eEncodingUint;
+
+ case clang::BuiltinType::NullPtr:
+ return lldb::eEncodingUint;
+
+ case clang::BuiltinType::Kind::ARCUnbridgedCast:
+ case clang::BuiltinType::Kind::BoundMember:
+ case clang::BuiltinType::Kind::BuiltinFn:
+ case clang::BuiltinType::Kind::Dependent:
+ case clang::BuiltinType::Kind::OCLClkEvent:
+ case clang::BuiltinType::Kind::OCLEvent:
+ case clang::BuiltinType::Kind::OCLImage1dRO:
+ case clang::BuiltinType::Kind::OCLImage1dWO:
+ case clang::BuiltinType::Kind::OCLImage1dRW:
+ case clang::BuiltinType::Kind::OCLImage1dArrayRO:
+ case clang::BuiltinType::Kind::OCLImage1dArrayWO:
+ case clang::BuiltinType::Kind::OCLImage1dArrayRW:
+ case clang::BuiltinType::Kind::OCLImage1dBufferRO:
+ case clang::BuiltinType::Kind::OCLImage1dBufferWO:
+ case clang::BuiltinType::Kind::OCLImage1dBufferRW:
+ case clang::BuiltinType::Kind::OCLImage2dRO:
+ case clang::BuiltinType::Kind::OCLImage2dWO:
+ case clang::BuiltinType::Kind::OCLImage2dRW:
+ case clang::BuiltinType::Kind::OCLImage2dArrayRO:
+ case clang::BuiltinType::Kind::OCLImage2dArrayWO:
+ case clang::BuiltinType::Kind::OCLImage2dArrayRW:
+ case clang::BuiltinType::Kind::OCLImage2dArrayDepthRO:
+ case clang::BuiltinType::Kind::OCLImage2dArrayDepthWO:
+ case clang::BuiltinType::Kind::OCLImage2dArrayDepthRW:
+ case clang::BuiltinType::Kind::OCLImage2dArrayMSAARO:
+ case clang::BuiltinType::Kind::OCLImage2dArrayMSAAWO:
+ case clang::BuiltinType::Kind::OCLImage2dArrayMSAARW:
+ case clang::BuiltinType::Kind::OCLImage2dArrayMSAADepthRO:
+ case clang::BuiltinType::Kind::OCLImage2dArrayMSAADepthWO:
+ case clang::BuiltinType::Kind::OCLImage2dArrayMSAADepthRW:
+ case clang::BuiltinType::Kind::OCLImage2dDepthRO:
+ case clang::BuiltinType::Kind::OCLImage2dDepthWO:
+ case clang::BuiltinType::Kind::OCLImage2dDepthRW:
+ case clang::BuiltinType::Kind::OCLImage2dMSAARO:
+ case clang::BuiltinType::Kind::OCLImage2dMSAAWO:
+ case clang::BuiltinType::Kind::OCLImage2dMSAARW:
+ case clang::BuiltinType::Kind::OCLImage2dMSAADepthRO:
+ case clang::BuiltinType::Kind::OCLImage2dMSAADepthWO:
+ case clang::BuiltinType::Kind::OCLImage2dMSAADepthRW:
+ case clang::BuiltinType::Kind::OCLImage3dRO:
+ case clang::BuiltinType::Kind::OCLImage3dWO:
+ case clang::BuiltinType::Kind::OCLImage3dRW:
+ case clang::BuiltinType::Kind::OCLQueue:
+ case clang::BuiltinType::Kind::OCLNDRange:
+ case clang::BuiltinType::Kind::OCLReserveID:
+ case clang::BuiltinType::Kind::OCLSampler:
+ case clang::BuiltinType::Kind::OMPArraySection:
+ case clang::BuiltinType::Kind::Overload:
+ case clang::BuiltinType::Kind::PseudoObject:
+ case clang::BuiltinType::Kind::UnknownAny:
+ break;
+ }
+ break;
+ // All pointer types are represented as unsigned integer encodings.
+ // We may nee to add a eEncodingPointer if we ever need to know the
+ // difference
+ case clang::Type::ObjCObjectPointer:
+ case clang::Type::BlockPointer:
+ case clang::Type::Pointer:
+ case clang::Type::LValueReference:
+ case clang::Type::RValueReference:
+ case clang::Type::MemberPointer:
+ return lldb::eEncodingUint;
+ case clang::Type::Complex: {
+ lldb::Encoding encoding = lldb::eEncodingIEEE754;
+ if (qual_type->isComplexType())
+ encoding = lldb::eEncodingIEEE754;
+ else {
+ const clang::ComplexType *complex_type =
+ qual_type->getAsComplexIntegerType();
+ if (complex_type)
+ encoding = CompilerType(getASTContext(), complex_type->getElementType())
+ .GetEncoding(count);
+ else
+ encoding = lldb::eEncodingSint;
+ }
+ count = 2;
+ return encoding;
+ }
+
+ case clang::Type::ObjCInterface:
+ break;
+ case clang::Type::Record:
+ break;
+ case clang::Type::Enum:
+ return lldb::eEncodingSint;
+ case clang::Type::Typedef:
+ return CompilerType(getASTContext(),
+ llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType())
+ .GetEncoding(count);
+
+ case clang::Type::Auto:
+ return CompilerType(
+ getASTContext(),
+ llvm::cast<clang::AutoType>(qual_type)->getDeducedType())
+ .GetEncoding(count);
+
+ case clang::Type::Elaborated:
+ return CompilerType(
+ getASTContext(),
+ llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType())
+ .GetEncoding(count);
+
+ case clang::Type::Paren:
+ return CompilerType(getASTContext(),
+ llvm::cast<clang::ParenType>(qual_type)->desugar())
+ .GetEncoding(count);
+
+ case clang::Type::DependentSizedArray:
+ case clang::Type::DependentSizedExtVector:
+ case clang::Type::UnresolvedUsing:
+ case clang::Type::Attributed:
+ case clang::Type::TemplateTypeParm:
+ case clang::Type::SubstTemplateTypeParm:
+ case clang::Type::SubstTemplateTypeParmPack:
+ case clang::Type::InjectedClassName:
+ case clang::Type::DependentName:
+ case clang::Type::DependentTemplateSpecialization:
+ case clang::Type::PackExpansion:
+ case clang::Type::ObjCObject:
+
+ case clang::Type::TypeOfExpr:
+ case clang::Type::TypeOf:
+ case clang::Type::Decltype:
+ case clang::Type::TemplateSpecialization:
+ case clang::Type::Atomic:
+ case clang::Type::Adjusted:
+ case clang::Type::Pipe:
+ break;
+
+ // pointer type decayed from an array or function type.
+ case clang::Type::Decayed:
+ break;
+ }
+ count = 0;
+ return lldb::eEncodingInvalid;
+}
+
+lldb::Format ClangASTContext::GetFormat(lldb::opaque_compiler_type_t type) {
+ if (!type)
+ return lldb::eFormatDefault;
+
+ clang::QualType qual_type(GetCanonicalQualType(type));
+
+ switch (qual_type->getTypeClass()) {
+ case clang::Type::UnaryTransform:
+ break;
+
+ case clang::Type::FunctionNoProto:
+ case clang::Type::FunctionProto:
+ break;
+
+ case clang::Type::IncompleteArray:
+ case clang::Type::VariableArray:
+ break;
+
+ case clang::Type::ConstantArray:
+ return lldb::eFormatVoid; // no value
+
+ case clang::Type::ExtVector:
+ case clang::Type::Vector:
+ break;
+
+ case clang::Type::Builtin:
+ switch (llvm::cast<clang::BuiltinType>(qual_type)->getKind()) {
+ // default: assert(0 && "Unknown builtin type!");
+ case clang::BuiltinType::UnknownAny:
+ case clang::BuiltinType::Void:
+ case clang::BuiltinType::BoundMember:
+ break;
+
+ case clang::BuiltinType::Bool:
+ return lldb::eFormatBoolean;
+ case clang::BuiltinType::Char_S:
+ case clang::BuiltinType::SChar:
+ case clang::BuiltinType::WChar_S:
+ case clang::BuiltinType::Char_U:
+ case clang::BuiltinType::UChar:
+ case clang::BuiltinType::WChar_U:
+ return lldb::eFormatChar;
+ case clang::BuiltinType::Char16:
+ return lldb::eFormatUnicode16;
+ case clang::BuiltinType::Char32:
+ return lldb::eFormatUnicode32;
+ case clang::BuiltinType::UShort:
+ return lldb::eFormatUnsigned;
+ case clang::BuiltinType::Short:
+ return lldb::eFormatDecimal;
+ case clang::BuiltinType::UInt:
+ return lldb::eFormatUnsigned;
+ case clang::BuiltinType::Int:
+ return lldb::eFormatDecimal;
+ case clang::BuiltinType::ULong:
+ return lldb::eFormatUnsigned;
+ case clang::BuiltinType::Long:
+ return lldb::eFormatDecimal;
+ case clang::BuiltinType::ULongLong:
+ return lldb::eFormatUnsigned;
+ case clang::BuiltinType::LongLong:
+ return lldb::eFormatDecimal;
+ case clang::BuiltinType::UInt128:
+ return lldb::eFormatUnsigned;
+ case clang::BuiltinType::Int128:
+ return lldb::eFormatDecimal;
+ case clang::BuiltinType::Half:
+ case clang::BuiltinType::Float:
+ case clang::BuiltinType::Double:
+ case clang::BuiltinType::LongDouble:
+ return lldb::eFormatFloat;
+ default:
+ return lldb::eFormatHex;
+ }
+ break;
+ case clang::Type::ObjCObjectPointer:
+ return lldb::eFormatHex;
+ case clang::Type::BlockPointer:
+ return lldb::eFormatHex;
+ case clang::Type::Pointer:
+ return lldb::eFormatHex;
+ case clang::Type::LValueReference:
+ case clang::Type::RValueReference:
+ return lldb::eFormatHex;
+ case clang::Type::MemberPointer:
+ break;
+ case clang::Type::Complex: {
+ if (qual_type->isComplexType())
+ return lldb::eFormatComplex;
+ else
+ return lldb::eFormatComplexInteger;
+ }
+ case clang::Type::ObjCInterface:
+ break;
+ case clang::Type::Record:
+ break;
+ case clang::Type::Enum:
+ return lldb::eFormatEnum;
+ case clang::Type::Typedef:
+ return CompilerType(getASTContext(),
+ llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType())
+ .GetFormat();
+ case clang::Type::Auto:
+ return CompilerType(getASTContext(),
+ llvm::cast<clang::AutoType>(qual_type)->desugar())
+ .GetFormat();
+ case clang::Type::Paren:
+ return CompilerType(getASTContext(),
+ llvm::cast<clang::ParenType>(qual_type)->desugar())
+ .GetFormat();
+ case clang::Type::Elaborated:
+ return CompilerType(
+ getASTContext(),
+ llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType())
+ .GetFormat();
+ case clang::Type::DependentSizedArray:
+ case clang::Type::DependentSizedExtVector:
+ case clang::Type::UnresolvedUsing:
+ case clang::Type::Attributed:
+ case clang::Type::TemplateTypeParm:
+ case clang::Type::SubstTemplateTypeParm:
+ case clang::Type::SubstTemplateTypeParmPack:
+ case clang::Type::InjectedClassName:
+ case clang::Type::DependentName:
+ case clang::Type::DependentTemplateSpecialization:
+ case clang::Type::PackExpansion:
+ case clang::Type::ObjCObject:
+
+ case clang::Type::TypeOfExpr:
+ case clang::Type::TypeOf:
+ case clang::Type::Decltype:
+ case clang::Type::TemplateSpecialization:
+ case clang::Type::Atomic:
+ case clang::Type::Adjusted:
+ case clang::Type::Pipe:
+ break;
+
+ // pointer type decayed from an array or function type.
+ case clang::Type::Decayed:
+ break;
+ }
+ // We don't know hot to display this type...
+ return lldb::eFormatBytes;
+}
+
+static bool ObjCDeclHasIVars(clang::ObjCInterfaceDecl *class_interface_decl,
+ bool check_superclass) {
+ while (class_interface_decl) {
+ if (class_interface_decl->ivar_size() > 0)
+ return true;
+
+ if (check_superclass)
+ class_interface_decl = class_interface_decl->getSuperClass();
+ else
+ break;
+ }
+ return false;
}
+uint32_t ClangASTContext::GetNumChildren(lldb::opaque_compiler_type_t type,
+ bool omit_empty_base_classes) {
+ if (!type)
+ return 0;
-lldb::Encoding
-ClangASTContext::GetEncoding (lldb::opaque_compiler_type_t type, uint64_t &count)
-{
- if (!type)
- return lldb::eEncodingInvalid;
-
- count = 1;
- clang::QualType qual_type(GetCanonicalQualType(type));
-
- switch (qual_type->getTypeClass())
- {
- case clang::Type::UnaryTransform:
- break;
-
- case clang::Type::FunctionNoProto:
- case clang::Type::FunctionProto:
- break;
-
- case clang::Type::IncompleteArray:
- case clang::Type::VariableArray:
- break;
-
- case clang::Type::ConstantArray:
- break;
-
- case clang::Type::ExtVector:
- case clang::Type::Vector:
- // TODO: Set this to more than one???
- break;
-
- case clang::Type::Builtin:
- switch (llvm::cast<clang::BuiltinType>(qual_type)->getKind())
- {
- case clang::BuiltinType::Void:
- break;
-
- case clang::BuiltinType::Bool:
- case clang::BuiltinType::Char_S:
- case clang::BuiltinType::SChar:
- case clang::BuiltinType::WChar_S:
- case clang::BuiltinType::Char16:
- case clang::BuiltinType::Char32:
- case clang::BuiltinType::Short:
- case clang::BuiltinType::Int:
- case clang::BuiltinType::Long:
- case clang::BuiltinType::LongLong:
- case clang::BuiltinType::Int128:
- return lldb::eEncodingSint;
-
- case clang::BuiltinType::Char_U:
- case clang::BuiltinType::UChar:
- case clang::BuiltinType::WChar_U:
- case clang::BuiltinType::UShort:
- case clang::BuiltinType::UInt:
- case clang::BuiltinType::ULong:
- case clang::BuiltinType::ULongLong:
- case clang::BuiltinType::UInt128:
- return lldb::eEncodingUint;
-
- case clang::BuiltinType::Half:
- case clang::BuiltinType::Float:
- case clang::BuiltinType::Float128:
- case clang::BuiltinType::Double:
- case clang::BuiltinType::LongDouble:
- return lldb::eEncodingIEEE754;
-
- case clang::BuiltinType::ObjCClass:
- case clang::BuiltinType::ObjCId:
- case clang::BuiltinType::ObjCSel:
- return lldb::eEncodingUint;
-
- case clang::BuiltinType::NullPtr:
- return lldb::eEncodingUint;
-
- case clang::BuiltinType::Kind::ARCUnbridgedCast:
- case clang::BuiltinType::Kind::BoundMember:
- case clang::BuiltinType::Kind::BuiltinFn:
- case clang::BuiltinType::Kind::Dependent:
- case clang::BuiltinType::Kind::OCLClkEvent:
- case clang::BuiltinType::Kind::OCLEvent:
- case clang::BuiltinType::Kind::OCLImage1dRO:
- case clang::BuiltinType::Kind::OCLImage1dWO:
- case clang::BuiltinType::Kind::OCLImage1dRW:
- case clang::BuiltinType::Kind::OCLImage1dArrayRO:
- case clang::BuiltinType::Kind::OCLImage1dArrayWO:
- case clang::BuiltinType::Kind::OCLImage1dArrayRW:
- case clang::BuiltinType::Kind::OCLImage1dBufferRO:
- case clang::BuiltinType::Kind::OCLImage1dBufferWO:
- case clang::BuiltinType::Kind::OCLImage1dBufferRW:
- case clang::BuiltinType::Kind::OCLImage2dRO:
- case clang::BuiltinType::Kind::OCLImage2dWO:
- case clang::BuiltinType::Kind::OCLImage2dRW:
- case clang::BuiltinType::Kind::OCLImage2dArrayRO:
- case clang::BuiltinType::Kind::OCLImage2dArrayWO:
- case clang::BuiltinType::Kind::OCLImage2dArrayRW:
- case clang::BuiltinType::Kind::OCLImage2dArrayDepthRO:
- case clang::BuiltinType::Kind::OCLImage2dArrayDepthWO:
- case clang::BuiltinType::Kind::OCLImage2dArrayDepthRW:
- case clang::BuiltinType::Kind::OCLImage2dArrayMSAARO:
- case clang::BuiltinType::Kind::OCLImage2dArrayMSAAWO:
- case clang::BuiltinType::Kind::OCLImage2dArrayMSAARW:
- case clang::BuiltinType::Kind::OCLImage2dArrayMSAADepthRO:
- case clang::BuiltinType::Kind::OCLImage2dArrayMSAADepthWO:
- case clang::BuiltinType::Kind::OCLImage2dArrayMSAADepthRW:
- case clang::BuiltinType::Kind::OCLImage2dDepthRO:
- case clang::BuiltinType::Kind::OCLImage2dDepthWO:
- case clang::BuiltinType::Kind::OCLImage2dDepthRW:
- case clang::BuiltinType::Kind::OCLImage2dMSAARO:
- case clang::BuiltinType::Kind::OCLImage2dMSAAWO:
- case clang::BuiltinType::Kind::OCLImage2dMSAARW:
- case clang::BuiltinType::Kind::OCLImage2dMSAADepthRO:
- case clang::BuiltinType::Kind::OCLImage2dMSAADepthWO:
- case clang::BuiltinType::Kind::OCLImage2dMSAADepthRW:
- case clang::BuiltinType::Kind::OCLImage3dRO:
- case clang::BuiltinType::Kind::OCLImage3dWO:
- case clang::BuiltinType::Kind::OCLImage3dRW:
- case clang::BuiltinType::Kind::OCLQueue:
- case clang::BuiltinType::Kind::OCLNDRange:
- case clang::BuiltinType::Kind::OCLReserveID:
- case clang::BuiltinType::Kind::OCLSampler:
- case clang::BuiltinType::Kind::OMPArraySection:
- case clang::BuiltinType::Kind::Overload:
- case clang::BuiltinType::Kind::PseudoObject:
- case clang::BuiltinType::Kind::UnknownAny:
- break;
- }
- break;
- // All pointer types are represented as unsigned integer encodings.
- // We may nee to add a eEncodingPointer if we ever need to know the
- // difference
- case clang::Type::ObjCObjectPointer:
- case clang::Type::BlockPointer:
- case clang::Type::Pointer:
- case clang::Type::LValueReference:
- case clang::Type::RValueReference:
- case clang::Type::MemberPointer: return lldb::eEncodingUint;
- case clang::Type::Complex:
- {
- lldb::Encoding encoding = lldb::eEncodingIEEE754;
- if (qual_type->isComplexType())
- encoding = lldb::eEncodingIEEE754;
- else
- {
- const clang::ComplexType *complex_type = qual_type->getAsComplexIntegerType();
- if (complex_type)
- encoding = CompilerType(getASTContext(), complex_type->getElementType()).GetEncoding(count);
- else
- encoding = lldb::eEncodingSint;
- }
- count = 2;
- return encoding;
- }
-
- case clang::Type::ObjCInterface: break;
- case clang::Type::Record: break;
- case clang::Type::Enum: return lldb::eEncodingSint;
- case clang::Type::Typedef:
- return CompilerType(getASTContext(), llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType()).GetEncoding(count);
-
- case clang::Type::Auto:
- return CompilerType(getASTContext(), llvm::cast<clang::AutoType>(qual_type)->getDeducedType()).GetEncoding(count);
-
- case clang::Type::Elaborated:
- return CompilerType(getASTContext(), llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType()).GetEncoding(count);
-
- case clang::Type::Paren:
- return CompilerType(getASTContext(), llvm::cast<clang::ParenType>(qual_type)->desugar()).GetEncoding(count);
-
- case clang::Type::DependentSizedArray:
- case clang::Type::DependentSizedExtVector:
- case clang::Type::UnresolvedUsing:
- case clang::Type::Attributed:
- case clang::Type::TemplateTypeParm:
- case clang::Type::SubstTemplateTypeParm:
- case clang::Type::SubstTemplateTypeParmPack:
- case clang::Type::InjectedClassName:
- case clang::Type::DependentName:
- case clang::Type::DependentTemplateSpecialization:
- case clang::Type::PackExpansion:
- case clang::Type::ObjCObject:
-
- case clang::Type::TypeOfExpr:
- case clang::Type::TypeOf:
- case clang::Type::Decltype:
- case clang::Type::TemplateSpecialization:
- case clang::Type::Atomic:
- case clang::Type::Adjusted:
- case clang::Type::Pipe:
- break;
+ uint32_t num_children = 0;
+ clang::QualType qual_type(GetQualType(type));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Builtin:
+ switch (llvm::cast<clang::BuiltinType>(qual_type)->getKind()) {
+ case clang::BuiltinType::ObjCId: // child is Class
+ case clang::BuiltinType::ObjCClass: // child is Class
+ num_children = 1;
+ break;
- // pointer type decayed from an array or function type.
- case clang::Type::Decayed:
- break;
+ default:
+ break;
}
- count = 0;
- return lldb::eEncodingInvalid;
-}
+ break;
-lldb::Format
-ClangASTContext::GetFormat (lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return lldb::eFormatDefault;
-
- clang::QualType qual_type(GetCanonicalQualType(type));
-
- switch (qual_type->getTypeClass())
- {
- case clang::Type::UnaryTransform:
- break;
-
- case clang::Type::FunctionNoProto:
- case clang::Type::FunctionProto:
- break;
-
- case clang::Type::IncompleteArray:
- case clang::Type::VariableArray:
- break;
-
- case clang::Type::ConstantArray:
- return lldb::eFormatVoid; // no value
-
- case clang::Type::ExtVector:
- case clang::Type::Vector:
- break;
-
- case clang::Type::Builtin:
- switch (llvm::cast<clang::BuiltinType>(qual_type)->getKind())
- {
- //default: assert(0 && "Unknown builtin type!");
- case clang::BuiltinType::UnknownAny:
- case clang::BuiltinType::Void:
- case clang::BuiltinType::BoundMember:
- break;
-
- case clang::BuiltinType::Bool: return lldb::eFormatBoolean;
- case clang::BuiltinType::Char_S:
- case clang::BuiltinType::SChar:
- case clang::BuiltinType::WChar_S:
- case clang::BuiltinType::Char_U:
- case clang::BuiltinType::UChar:
- case clang::BuiltinType::WChar_U: return lldb::eFormatChar;
- case clang::BuiltinType::Char16: return lldb::eFormatUnicode16;
- case clang::BuiltinType::Char32: return lldb::eFormatUnicode32;
- case clang::BuiltinType::UShort: return lldb::eFormatUnsigned;
- case clang::BuiltinType::Short: return lldb::eFormatDecimal;
- case clang::BuiltinType::UInt: return lldb::eFormatUnsigned;
- case clang::BuiltinType::Int: return lldb::eFormatDecimal;
- case clang::BuiltinType::ULong: return lldb::eFormatUnsigned;
- case clang::BuiltinType::Long: return lldb::eFormatDecimal;
- case clang::BuiltinType::ULongLong: return lldb::eFormatUnsigned;
- case clang::BuiltinType::LongLong: return lldb::eFormatDecimal;
- case clang::BuiltinType::UInt128: return lldb::eFormatUnsigned;
- case clang::BuiltinType::Int128: return lldb::eFormatDecimal;
- case clang::BuiltinType::Half:
- case clang::BuiltinType::Float:
- case clang::BuiltinType::Double:
- case clang::BuiltinType::LongDouble: return lldb::eFormatFloat;
- default:
- return lldb::eFormatHex;
+ case clang::Type::Complex:
+ return 0;
+
+ case clang::Type::Record:
+ if (GetCompleteQualType(getASTContext(), qual_type)) {
+ const clang::RecordType *record_type =
+ llvm::cast<clang::RecordType>(qual_type.getTypePtr());
+ const clang::RecordDecl *record_decl = record_type->getDecl();
+ assert(record_decl);
+ const clang::CXXRecordDecl *cxx_record_decl =
+ llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
+ if (cxx_record_decl) {
+ if (omit_empty_base_classes) {
+ // Check each base classes to see if it or any of its
+ // base classes contain any fields. This can help
+ // limit the noise in variable views by not having to
+ // show base classes that contain no members.
+ clang::CXXRecordDecl::base_class_const_iterator base_class,
+ base_class_end;
+ for (base_class = cxx_record_decl->bases_begin(),
+ base_class_end = cxx_record_decl->bases_end();
+ base_class != base_class_end; ++base_class) {
+ const clang::CXXRecordDecl *base_class_decl =
+ llvm::cast<clang::CXXRecordDecl>(
+ base_class->getType()
+ ->getAs<clang::RecordType>()
+ ->getDecl());
+
+ // Skip empty base classes
+ if (ClangASTContext::RecordHasFields(base_class_decl) == false)
+ continue;
+
+ num_children++;
+ }
+ } else {
+ // Include all base classes
+ num_children += cxx_record_decl->getNumBases();
}
- break;
- case clang::Type::ObjCObjectPointer: return lldb::eFormatHex;
- case clang::Type::BlockPointer: return lldb::eFormatHex;
- case clang::Type::Pointer: return lldb::eFormatHex;
- case clang::Type::LValueReference:
- case clang::Type::RValueReference: return lldb::eFormatHex;
- case clang::Type::MemberPointer: break;
- case clang::Type::Complex:
- {
- if (qual_type->isComplexType())
- return lldb::eFormatComplex;
- else
- return lldb::eFormatComplexInteger;
+ }
+ clang::RecordDecl::field_iterator field, field_end;
+ for (field = record_decl->field_begin(),
+ field_end = record_decl->field_end();
+ field != field_end; ++field)
+ ++num_children;
+ }
+ break;
+
+ case clang::Type::ObjCObject:
+ case clang::Type::ObjCInterface:
+ if (GetCompleteQualType(getASTContext(), qual_type)) {
+ const clang::ObjCObjectType *objc_class_type =
+ llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
+ assert(objc_class_type);
+ if (objc_class_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterface();
+
+ if (class_interface_decl) {
+
+ clang::ObjCInterfaceDecl *superclass_interface_decl =
+ class_interface_decl->getSuperClass();
+ if (superclass_interface_decl) {
+ if (omit_empty_base_classes) {
+ if (ObjCDeclHasIVars(superclass_interface_decl, true))
+ ++num_children;
+ } else
+ ++num_children;
+ }
+
+ num_children += class_interface_decl->ivar_size();
}
- case clang::Type::ObjCInterface: break;
- case clang::Type::Record: break;
- case clang::Type::Enum: return lldb::eFormatEnum;
- case clang::Type::Typedef:
- return CompilerType (getASTContext(), llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType()).GetFormat();
- case clang::Type::Auto:
- return CompilerType (getASTContext(), llvm::cast<clang::AutoType>(qual_type)->desugar()).GetFormat();
- case clang::Type::Paren:
- return CompilerType (getASTContext(), llvm::cast<clang::ParenType>(qual_type)->desugar()).GetFormat();
- case clang::Type::Elaborated:
- return CompilerType (getASTContext(), llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType()).GetFormat();
- case clang::Type::DependentSizedArray:
- case clang::Type::DependentSizedExtVector:
- case clang::Type::UnresolvedUsing:
- case clang::Type::Attributed:
- case clang::Type::TemplateTypeParm:
- case clang::Type::SubstTemplateTypeParm:
- case clang::Type::SubstTemplateTypeParmPack:
- case clang::Type::InjectedClassName:
- case clang::Type::DependentName:
- case clang::Type::DependentTemplateSpecialization:
- case clang::Type::PackExpansion:
- case clang::Type::ObjCObject:
-
- case clang::Type::TypeOfExpr:
- case clang::Type::TypeOf:
- case clang::Type::Decltype:
- case clang::Type::TemplateSpecialization:
- case clang::Type::Atomic:
- case clang::Type::Adjusted:
- case clang::Type::Pipe:
- break;
-
- // pointer type decayed from an array or function type.
- case clang::Type::Decayed:
- break;
- }
- // We don't know hot to display this type...
- return lldb::eFormatBytes;
-}
-
-static bool
-ObjCDeclHasIVars (clang::ObjCInterfaceDecl *class_interface_decl, bool check_superclass)
-{
- while (class_interface_decl)
- {
- if (class_interface_decl->ivar_size() > 0)
- return true;
-
- if (check_superclass)
- class_interface_decl = class_interface_decl->getSuperClass();
- else
- break;
- }
- return false;
+ }
+ }
+ break;
+
+ case clang::Type::ObjCObjectPointer: {
+ const clang::ObjCObjectPointerType *pointer_type =
+ llvm::cast<clang::ObjCObjectPointerType>(qual_type.getTypePtr());
+ clang::QualType pointee_type = pointer_type->getPointeeType();
+ uint32_t num_pointee_children =
+ CompilerType(getASTContext(), pointee_type)
+ .GetNumChildren(omit_empty_base_classes);
+ // If this type points to a simple type, then it has 1 child
+ if (num_pointee_children == 0)
+ num_children = 1;
+ else
+ num_children = num_pointee_children;
+ } break;
+
+ case clang::Type::Vector:
+ case clang::Type::ExtVector:
+ num_children =
+ llvm::cast<clang::VectorType>(qual_type.getTypePtr())->getNumElements();
+ break;
+
+ case clang::Type::ConstantArray:
+ num_children = llvm::cast<clang::ConstantArrayType>(qual_type.getTypePtr())
+ ->getSize()
+ .getLimitedValue();
+ break;
+
+ case clang::Type::Pointer: {
+ const clang::PointerType *pointer_type =
+ llvm::cast<clang::PointerType>(qual_type.getTypePtr());
+ clang::QualType pointee_type(pointer_type->getPointeeType());
+ uint32_t num_pointee_children =
+ CompilerType(getASTContext(), pointee_type)
+ .GetNumChildren(omit_empty_base_classes);
+ if (num_pointee_children == 0) {
+ // We have a pointer to a pointee type that claims it has no children.
+ // We will want to look at
+ num_children = GetNumPointeeChildren(pointee_type);
+ } else
+ num_children = num_pointee_children;
+ } break;
+
+ case clang::Type::LValueReference:
+ case clang::Type::RValueReference: {
+ const clang::ReferenceType *reference_type =
+ llvm::cast<clang::ReferenceType>(qual_type.getTypePtr());
+ clang::QualType pointee_type = reference_type->getPointeeType();
+ uint32_t num_pointee_children =
+ CompilerType(getASTContext(), pointee_type)
+ .GetNumChildren(omit_empty_base_classes);
+ // If this type points to a simple type, then it has 1 child
+ if (num_pointee_children == 0)
+ num_children = 1;
+ else
+ num_children = num_pointee_children;
+ } break;
+
+ case clang::Type::Typedef:
+ num_children =
+ CompilerType(getASTContext(), llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType())
+ .GetNumChildren(omit_empty_base_classes);
+ break;
+
+ case clang::Type::Auto:
+ num_children =
+ CompilerType(getASTContext(),
+ llvm::cast<clang::AutoType>(qual_type)->getDeducedType())
+ .GetNumChildren(omit_empty_base_classes);
+ break;
+
+ case clang::Type::Elaborated:
+ num_children =
+ CompilerType(
+ getASTContext(),
+ llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType())
+ .GetNumChildren(omit_empty_base_classes);
+ break;
+
+ case clang::Type::Paren:
+ num_children =
+ CompilerType(getASTContext(),
+ llvm::cast<clang::ParenType>(qual_type)->desugar())
+ .GetNumChildren(omit_empty_base_classes);
+ break;
+ default:
+ break;
+ }
+ return num_children;
+}
+
+CompilerType ClangASTContext::GetBuiltinTypeByName(const ConstString &name) {
+ return GetBasicType(GetBasicTypeEnumeration(name));
}
-uint32_t
-ClangASTContext::GetNumChildren (lldb::opaque_compiler_type_t type, bool omit_empty_base_classes)
-{
- if (!type)
- return 0;
-
- uint32_t num_children = 0;
+lldb::BasicType
+ClangASTContext::GetBasicTypeEnumeration(lldb::opaque_compiler_type_t type) {
+ if (type) {
clang::QualType qual_type(GetQualType(type));
const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Builtin:
- switch (llvm::cast<clang::BuiltinType>(qual_type)->getKind())
- {
- case clang::BuiltinType::ObjCId: // child is Class
- case clang::BuiltinType::ObjCClass: // child is Class
- num_children = 1;
- break;
-
- default:
- break;
- }
- break;
-
- case clang::Type::Complex: return 0;
-
- case clang::Type::Record:
- if (GetCompleteQualType (getASTContext(), qual_type))
- {
- const clang::RecordType *record_type = llvm::cast<clang::RecordType>(qual_type.getTypePtr());
- const clang::RecordDecl *record_decl = record_type->getDecl();
- assert(record_decl);
- const clang::CXXRecordDecl *cxx_record_decl = llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
- if (cxx_record_decl)
- {
- if (omit_empty_base_classes)
- {
- // Check each base classes to see if it or any of its
- // base classes contain any fields. This can help
- // limit the noise in variable views by not having to
- // show base classes that contain no members.
- clang::CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
- for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end();
- base_class != base_class_end;
- ++base_class)
- {
- const clang::CXXRecordDecl *base_class_decl = llvm::cast<clang::CXXRecordDecl>(base_class->getType()->getAs<clang::RecordType>()->getDecl());
-
- // Skip empty base classes
- if (ClangASTContext::RecordHasFields(base_class_decl) == false)
- continue;
-
- num_children++;
- }
- }
- else
- {
- // Include all base classes
- num_children += cxx_record_decl->getNumBases();
- }
-
- }
- clang::RecordDecl::field_iterator field, field_end;
- for (field = record_decl->field_begin(), field_end = record_decl->field_end(); field != field_end; ++field)
- ++num_children;
- }
- break;
-
- case clang::Type::ObjCObject:
- case clang::Type::ObjCInterface:
- if (GetCompleteQualType (getASTContext(), qual_type))
- {
- const clang::ObjCObjectType *objc_class_type = llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
- assert (objc_class_type);
- if (objc_class_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
-
- if (class_interface_decl)
- {
-
- clang::ObjCInterfaceDecl *superclass_interface_decl = class_interface_decl->getSuperClass();
- if (superclass_interface_decl)
- {
- if (omit_empty_base_classes)
- {
- if (ObjCDeclHasIVars (superclass_interface_decl, true))
- ++num_children;
- }
- else
- ++num_children;
- }
-
- num_children += class_interface_decl->ivar_size();
- }
- }
- }
- break;
-
- case clang::Type::ObjCObjectPointer:
- {
- const clang::ObjCObjectPointerType *pointer_type = llvm::cast<clang::ObjCObjectPointerType>(qual_type.getTypePtr());
- clang::QualType pointee_type = pointer_type->getPointeeType();
- uint32_t num_pointee_children = CompilerType (getASTContext(),pointee_type).GetNumChildren (omit_empty_base_classes);
- // If this type points to a simple type, then it has 1 child
- if (num_pointee_children == 0)
- num_children = 1;
- else
- num_children = num_pointee_children;
- }
- break;
-
- case clang::Type::Vector:
- case clang::Type::ExtVector:
- num_children = llvm::cast<clang::VectorType>(qual_type.getTypePtr())->getNumElements();
- break;
-
- case clang::Type::ConstantArray:
- num_children = llvm::cast<clang::ConstantArrayType>(qual_type.getTypePtr())->getSize().getLimitedValue();
- break;
-
- case clang::Type::Pointer:
- {
- const clang::PointerType *pointer_type = llvm::cast<clang::PointerType>(qual_type.getTypePtr());
- clang::QualType pointee_type (pointer_type->getPointeeType());
- uint32_t num_pointee_children = CompilerType (getASTContext(),pointee_type).GetNumChildren (omit_empty_base_classes);
- if (num_pointee_children == 0)
- {
- // We have a pointer to a pointee type that claims it has no children.
- // We will want to look at
- num_children = GetNumPointeeChildren (pointee_type);
- }
- else
- num_children = num_pointee_children;
- }
- break;
-
- case clang::Type::LValueReference:
- case clang::Type::RValueReference:
- {
- const clang::ReferenceType *reference_type = llvm::cast<clang::ReferenceType>(qual_type.getTypePtr());
- clang::QualType pointee_type = reference_type->getPointeeType();
- uint32_t num_pointee_children = CompilerType (getASTContext(), pointee_type).GetNumChildren (omit_empty_base_classes);
- // If this type points to a simple type, then it has 1 child
- if (num_pointee_children == 0)
- num_children = 1;
- else
- num_children = num_pointee_children;
- }
- break;
-
-
- case clang::Type::Typedef:
- num_children = CompilerType (getASTContext(), llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType()).GetNumChildren (omit_empty_base_classes);
- break;
-
- case clang::Type::Auto:
- num_children = CompilerType (getASTContext(), llvm::cast<clang::AutoType>(qual_type)->getDeducedType()).GetNumChildren (omit_empty_base_classes);
- break;
-
- case clang::Type::Elaborated:
- num_children = CompilerType (getASTContext(), llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType()).GetNumChildren (omit_empty_base_classes);
- break;
-
- case clang::Type::Paren:
- num_children = CompilerType (getASTContext(), llvm::cast<clang::ParenType>(qual_type)->desugar()).GetNumChildren (omit_empty_base_classes);
- break;
- default:
- break;
- }
- return num_children;
+ if (type_class == clang::Type::Builtin) {
+ switch (llvm::cast<clang::BuiltinType>(qual_type)->getKind()) {
+ case clang::BuiltinType::Void:
+ return eBasicTypeVoid;
+ case clang::BuiltinType::Bool:
+ return eBasicTypeBool;
+ case clang::BuiltinType::Char_S:
+ return eBasicTypeSignedChar;
+ case clang::BuiltinType::Char_U:
+ return eBasicTypeUnsignedChar;
+ case clang::BuiltinType::Char16:
+ return eBasicTypeChar16;
+ case clang::BuiltinType::Char32:
+ return eBasicTypeChar32;
+ case clang::BuiltinType::UChar:
+ return eBasicTypeUnsignedChar;
+ case clang::BuiltinType::SChar:
+ return eBasicTypeSignedChar;
+ case clang::BuiltinType::WChar_S:
+ return eBasicTypeSignedWChar;
+ case clang::BuiltinType::WChar_U:
+ return eBasicTypeUnsignedWChar;
+ case clang::BuiltinType::Short:
+ return eBasicTypeShort;
+ case clang::BuiltinType::UShort:
+ return eBasicTypeUnsignedShort;
+ case clang::BuiltinType::Int:
+ return eBasicTypeInt;
+ case clang::BuiltinType::UInt:
+ return eBasicTypeUnsignedInt;
+ case clang::BuiltinType::Long:
+ return eBasicTypeLong;
+ case clang::BuiltinType::ULong:
+ return eBasicTypeUnsignedLong;
+ case clang::BuiltinType::LongLong:
+ return eBasicTypeLongLong;
+ case clang::BuiltinType::ULongLong:
+ return eBasicTypeUnsignedLongLong;
+ case clang::BuiltinType::Int128:
+ return eBasicTypeInt128;
+ case clang::BuiltinType::UInt128:
+ return eBasicTypeUnsignedInt128;
+
+ case clang::BuiltinType::Half:
+ return eBasicTypeHalf;
+ case clang::BuiltinType::Float:
+ return eBasicTypeFloat;
+ case clang::BuiltinType::Double:
+ return eBasicTypeDouble;
+ case clang::BuiltinType::LongDouble:
+ return eBasicTypeLongDouble;
+
+ case clang::BuiltinType::NullPtr:
+ return eBasicTypeNullPtr;
+ case clang::BuiltinType::ObjCId:
+ return eBasicTypeObjCID;
+ case clang::BuiltinType::ObjCClass:
+ return eBasicTypeObjCClass;
+ case clang::BuiltinType::ObjCSel:
+ return eBasicTypeObjCSel;
+ default:
+ return eBasicTypeOther;
+ }
+ }
+ }
+ return eBasicTypeInvalid;
+}
+
+void ClangASTContext::ForEachEnumerator(
+ lldb::opaque_compiler_type_t type,
+ std::function<bool(const CompilerType &integer_type,
+ const ConstString &name,
+ const llvm::APSInt &value)> const &callback) {
+ const clang::EnumType *enum_type =
+ llvm::dyn_cast<clang::EnumType>(GetCanonicalQualType(type));
+ if (enum_type) {
+ const clang::EnumDecl *enum_decl = enum_type->getDecl();
+ if (enum_decl) {
+ CompilerType integer_type(this,
+ enum_decl->getIntegerType().getAsOpaquePtr());
+
+ clang::EnumDecl::enumerator_iterator enum_pos, enum_end_pos;
+ for (enum_pos = enum_decl->enumerator_begin(),
+ enum_end_pos = enum_decl->enumerator_end();
+ enum_pos != enum_end_pos; ++enum_pos) {
+ ConstString name(enum_pos->getNameAsString().c_str());
+ if (!callback(integer_type, name, enum_pos->getInitVal()))
+ break;
+ }
+ }
+ }
}
-CompilerType
-ClangASTContext::GetBuiltinTypeByName (const ConstString &name)
-{
- return GetBasicType(GetBasicTypeEnumeration(name));
-}
+#pragma mark Aggregate Types
-lldb::BasicType
-ClangASTContext::GetBasicTypeEnumeration (lldb::opaque_compiler_type_t type)
-{
- if (type)
- {
- clang::QualType qual_type(GetQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- if (type_class == clang::Type::Builtin)
- {
- switch (llvm::cast<clang::BuiltinType>(qual_type)->getKind())
- {
- case clang::BuiltinType::Void: return eBasicTypeVoid;
- case clang::BuiltinType::Bool: return eBasicTypeBool;
- case clang::BuiltinType::Char_S: return eBasicTypeSignedChar;
- case clang::BuiltinType::Char_U: return eBasicTypeUnsignedChar;
- case clang::BuiltinType::Char16: return eBasicTypeChar16;
- case clang::BuiltinType::Char32: return eBasicTypeChar32;
- case clang::BuiltinType::UChar: return eBasicTypeUnsignedChar;
- case clang::BuiltinType::SChar: return eBasicTypeSignedChar;
- case clang::BuiltinType::WChar_S: return eBasicTypeSignedWChar;
- case clang::BuiltinType::WChar_U: return eBasicTypeUnsignedWChar;
- case clang::BuiltinType::Short: return eBasicTypeShort;
- case clang::BuiltinType::UShort: return eBasicTypeUnsignedShort;
- case clang::BuiltinType::Int: return eBasicTypeInt;
- case clang::BuiltinType::UInt: return eBasicTypeUnsignedInt;
- case clang::BuiltinType::Long: return eBasicTypeLong;
- case clang::BuiltinType::ULong: return eBasicTypeUnsignedLong;
- case clang::BuiltinType::LongLong: return eBasicTypeLongLong;
- case clang::BuiltinType::ULongLong: return eBasicTypeUnsignedLongLong;
- case clang::BuiltinType::Int128: return eBasicTypeInt128;
- case clang::BuiltinType::UInt128: return eBasicTypeUnsignedInt128;
-
- case clang::BuiltinType::Half: return eBasicTypeHalf;
- case clang::BuiltinType::Float: return eBasicTypeFloat;
- case clang::BuiltinType::Double: return eBasicTypeDouble;
- case clang::BuiltinType::LongDouble:return eBasicTypeLongDouble;
-
- case clang::BuiltinType::NullPtr: return eBasicTypeNullPtr;
- case clang::BuiltinType::ObjCId: return eBasicTypeObjCID;
- case clang::BuiltinType::ObjCClass: return eBasicTypeObjCClass;
- case clang::BuiltinType::ObjCSel: return eBasicTypeObjCSel;
- default:
- return eBasicTypeOther;
- }
- }
- }
- return eBasicTypeInvalid;
-}
-
-void
-ClangASTContext::ForEachEnumerator (lldb::opaque_compiler_type_t type, std::function <bool (const CompilerType &integer_type, const ConstString &name, const llvm::APSInt &value)> const &callback)
-{
- const clang::EnumType *enum_type = llvm::dyn_cast<clang::EnumType>(GetCanonicalQualType(type));
- if (enum_type)
- {
- const clang::EnumDecl *enum_decl = enum_type->getDecl();
- if (enum_decl)
- {
- CompilerType integer_type(this, enum_decl->getIntegerType().getAsOpaquePtr());
-
- clang::EnumDecl::enumerator_iterator enum_pos, enum_end_pos;
- for (enum_pos = enum_decl->enumerator_begin(), enum_end_pos = enum_decl->enumerator_end(); enum_pos != enum_end_pos; ++enum_pos)
- {
- ConstString name(enum_pos->getNameAsString().c_str());
- if (!callback (integer_type, name, enum_pos->getInitVal()))
- break;
- }
- }
- }
-}
+uint32_t ClangASTContext::GetNumFields(lldb::opaque_compiler_type_t type) {
+ if (!type)
+ return 0;
+ uint32_t count = 0;
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Record:
+ if (GetCompleteType(type)) {
+ const clang::RecordType *record_type =
+ llvm::dyn_cast<clang::RecordType>(qual_type.getTypePtr());
+ if (record_type) {
+ clang::RecordDecl *record_decl = record_type->getDecl();
+ if (record_decl) {
+ uint32_t field_idx = 0;
+ clang::RecordDecl::field_iterator field, field_end;
+ for (field = record_decl->field_begin(),
+ field_end = record_decl->field_end();
+ field != field_end; ++field)
+ ++field_idx;
+ count = field_idx;
+ }
+ }
+ }
+ break;
+
+ case clang::Type::Typedef:
+ count =
+ CompilerType(getASTContext(), llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType())
+ .GetNumFields();
+ break;
+
+ case clang::Type::Auto:
+ count =
+ CompilerType(getASTContext(),
+ llvm::cast<clang::AutoType>(qual_type)->getDeducedType())
+ .GetNumFields();
+ break;
+
+ case clang::Type::Elaborated:
+ count = CompilerType(
+ getASTContext(),
+ llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType())
+ .GetNumFields();
+ break;
+
+ case clang::Type::Paren:
+ count = CompilerType(getASTContext(),
+ llvm::cast<clang::ParenType>(qual_type)->desugar())
+ .GetNumFields();
+ break;
+
+ case clang::Type::ObjCObjectPointer:
+ if (GetCompleteType(type)) {
+ const clang::ObjCObjectPointerType *objc_class_type =
+ qual_type->getAsObjCInterfacePointerType();
+ if (objc_class_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterfaceDecl();
-#pragma mark Aggregate Types
+ if (class_interface_decl)
+ count = class_interface_decl->ivar_size();
+ }
+ }
+ break;
-uint32_t
-ClangASTContext::GetNumFields (lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return 0;
-
- uint32_t count = 0;
- clang::QualType qual_type(GetCanonicalQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Record:
- if (GetCompleteType(type))
- {
- const clang::RecordType *record_type = llvm::dyn_cast<clang::RecordType>(qual_type.getTypePtr());
- if (record_type)
- {
- clang::RecordDecl *record_decl = record_type->getDecl();
- if (record_decl)
- {
- uint32_t field_idx = 0;
- clang::RecordDecl::field_iterator field, field_end;
- for (field = record_decl->field_begin(), field_end = record_decl->field_end(); field != field_end; ++field)
- ++field_idx;
- count = field_idx;
- }
- }
- }
- break;
-
- case clang::Type::Typedef:
- count = CompilerType (getASTContext(), llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType()).GetNumFields();
- break;
+ case clang::Type::ObjCObject:
+ case clang::Type::ObjCInterface:
+ if (GetCompleteType(type)) {
+ const clang::ObjCObjectType *objc_class_type =
+ llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
+ if (objc_class_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterface();
- case clang::Type::Auto:
- count = CompilerType (getASTContext(), llvm::cast<clang::AutoType>(qual_type)->getDeducedType()).GetNumFields();
- break;
-
- case clang::Type::Elaborated:
- count = CompilerType (getASTContext(), llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType()).GetNumFields();
- break;
-
- case clang::Type::Paren:
- count = CompilerType (getASTContext(), llvm::cast<clang::ParenType>(qual_type)->desugar()).GetNumFields();
- break;
-
- case clang::Type::ObjCObjectPointer:
- if (GetCompleteType(type))
- {
- const clang::ObjCObjectPointerType *objc_class_type = qual_type->getAsObjCInterfacePointerType();
- if (objc_class_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterfaceDecl();
-
- if (class_interface_decl)
- count = class_interface_decl->ivar_size();
- }
- }
- break;
-
- case clang::Type::ObjCObject:
- case clang::Type::ObjCInterface:
- if (GetCompleteType(type))
- {
- const clang::ObjCObjectType *objc_class_type = llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
- if (objc_class_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
-
- if (class_interface_decl)
- count = class_interface_decl->ivar_size();
- }
- }
- break;
-
- default:
- break;
+ if (class_interface_decl)
+ count = class_interface_decl->ivar_size();
+ }
}
- return count;
+ break;
+
+ default:
+ break;
+ }
+ return count;
}
static lldb::opaque_compiler_type_t
-GetObjCFieldAtIndex (clang::ASTContext *ast,
- clang::ObjCInterfaceDecl *class_interface_decl,
- size_t idx,
- std::string& name,
- uint64_t *bit_offset_ptr,
- uint32_t *bitfield_bit_size_ptr,
- bool *is_bitfield_ptr)
-{
- if (class_interface_decl)
- {
- if (idx < (class_interface_decl->ivar_size()))
- {
- clang::ObjCInterfaceDecl::ivar_iterator ivar_pos, ivar_end = class_interface_decl->ivar_end();
- uint32_t ivar_idx = 0;
-
- for (ivar_pos = class_interface_decl->ivar_begin(); ivar_pos != ivar_end; ++ivar_pos, ++ivar_idx)
- {
- if (ivar_idx == idx)
- {
- const clang::ObjCIvarDecl* ivar_decl = *ivar_pos;
-
- clang::QualType ivar_qual_type(ivar_decl->getType());
-
- name.assign(ivar_decl->getNameAsString());
-
- if (bit_offset_ptr)
- {
- const clang::ASTRecordLayout &interface_layout = ast->getASTObjCInterfaceLayout(class_interface_decl);
- *bit_offset_ptr = interface_layout.getFieldOffset (ivar_idx);
- }
-
- const bool is_bitfield = ivar_pos->isBitField();
-
- if (bitfield_bit_size_ptr)
- {
- *bitfield_bit_size_ptr = 0;
-
- if (is_bitfield && ast)
- {
- clang::Expr *bitfield_bit_size_expr = ivar_pos->getBitWidth();
- llvm::APSInt bitfield_apsint;
- if (bitfield_bit_size_expr && bitfield_bit_size_expr->EvaluateAsInt(bitfield_apsint, *ast))
- {
- *bitfield_bit_size_ptr = bitfield_apsint.getLimitedValue();
- }
- }
- }
- if (is_bitfield_ptr)
- *is_bitfield_ptr = is_bitfield;
-
- return ivar_qual_type.getAsOpaquePtr();
- }
+GetObjCFieldAtIndex(clang::ASTContext *ast,
+ clang::ObjCInterfaceDecl *class_interface_decl, size_t idx,
+ std::string &name, uint64_t *bit_offset_ptr,
+ uint32_t *bitfield_bit_size_ptr, bool *is_bitfield_ptr) {
+ if (class_interface_decl) {
+ if (idx < (class_interface_decl->ivar_size())) {
+ clang::ObjCInterfaceDecl::ivar_iterator ivar_pos,
+ ivar_end = class_interface_decl->ivar_end();
+ uint32_t ivar_idx = 0;
+
+ for (ivar_pos = class_interface_decl->ivar_begin(); ivar_pos != ivar_end;
+ ++ivar_pos, ++ivar_idx) {
+ if (ivar_idx == idx) {
+ const clang::ObjCIvarDecl *ivar_decl = *ivar_pos;
+
+ clang::QualType ivar_qual_type(ivar_decl->getType());
+
+ name.assign(ivar_decl->getNameAsString());
+
+ if (bit_offset_ptr) {
+ const clang::ASTRecordLayout &interface_layout =
+ ast->getASTObjCInterfaceLayout(class_interface_decl);
+ *bit_offset_ptr = interface_layout.getFieldOffset(ivar_idx);
+ }
+
+ const bool is_bitfield = ivar_pos->isBitField();
+
+ if (bitfield_bit_size_ptr) {
+ *bitfield_bit_size_ptr = 0;
+
+ if (is_bitfield && ast) {
+ clang::Expr *bitfield_bit_size_expr = ivar_pos->getBitWidth();
+ llvm::APSInt bitfield_apsint;
+ if (bitfield_bit_size_expr &&
+ bitfield_bit_size_expr->EvaluateAsInt(bitfield_apsint,
+ *ast)) {
+ *bitfield_bit_size_ptr = bitfield_apsint.getLimitedValue();
+ }
}
+ }
+ if (is_bitfield_ptr)
+ *is_bitfield_ptr = is_bitfield;
+
+ return ivar_qual_type.getAsOpaquePtr();
}
+ }
}
- return nullptr;
+ }
+ return nullptr;
}
-CompilerType
-ClangASTContext::GetFieldAtIndex (lldb::opaque_compiler_type_t type, size_t idx,
- std::string& name,
- uint64_t *bit_offset_ptr,
- uint32_t *bitfield_bit_size_ptr,
- bool *is_bitfield_ptr)
-{
- if (!type)
- return CompilerType();
-
- clang::QualType qual_type(GetCanonicalQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Record:
- if (GetCompleteType(type))
- {
- const clang::RecordType *record_type = llvm::cast<clang::RecordType>(qual_type.getTypePtr());
- const clang::RecordDecl *record_decl = record_type->getDecl();
- uint32_t field_idx = 0;
- clang::RecordDecl::field_iterator field, field_end;
- for (field = record_decl->field_begin(), field_end = record_decl->field_end(); field != field_end; ++field, ++field_idx)
- {
- if (idx == field_idx)
- {
- // Print the member type if requested
- // Print the member name and equal sign
- name.assign(field->getNameAsString());
-
- // Figure out the type byte size (field_type_info.first) and
- // alignment (field_type_info.second) from the AST context.
- if (bit_offset_ptr)
- {
- const clang::ASTRecordLayout &record_layout = getASTContext()->getASTRecordLayout(record_decl);
- *bit_offset_ptr = record_layout.getFieldOffset (field_idx);
- }
-
- const bool is_bitfield = field->isBitField();
-
- if (bitfield_bit_size_ptr)
- {
- *bitfield_bit_size_ptr = 0;
-
- if (is_bitfield)
- {
- clang::Expr *bitfield_bit_size_expr = field->getBitWidth();
- llvm::APSInt bitfield_apsint;
- if (bitfield_bit_size_expr && bitfield_bit_size_expr->EvaluateAsInt(bitfield_apsint, *getASTContext()))
- {
- *bitfield_bit_size_ptr = bitfield_apsint.getLimitedValue();
- }
- }
- }
- if (is_bitfield_ptr)
- *is_bitfield_ptr = is_bitfield;
-
- return CompilerType (getASTContext(), field->getType());
- }
- }
- }
- break;
-
- case clang::Type::ObjCObjectPointer:
- if (GetCompleteType(type))
- {
- const clang::ObjCObjectPointerType *objc_class_type = qual_type->getAsObjCInterfacePointerType();
- if (objc_class_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterfaceDecl();
- return CompilerType (this, GetObjCFieldAtIndex(getASTContext(), class_interface_decl, idx, name, bit_offset_ptr, bitfield_bit_size_ptr, is_bitfield_ptr));
- }
- }
- break;
-
- case clang::Type::ObjCObject:
- case clang::Type::ObjCInterface:
- if (GetCompleteType(type))
- {
- const clang::ObjCObjectType *objc_class_type = llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
- assert (objc_class_type);
- if (objc_class_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
- return CompilerType (this, GetObjCFieldAtIndex(getASTContext(), class_interface_decl, idx, name, bit_offset_ptr, bitfield_bit_size_ptr, is_bitfield_ptr));
- }
- }
- break;
-
-
- case clang::Type::Typedef:
- return CompilerType (getASTContext(), llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType()).
- GetFieldAtIndex (idx,
- name,
- bit_offset_ptr,
- bitfield_bit_size_ptr,
- is_bitfield_ptr);
-
- case clang::Type::Auto:
- return CompilerType (getASTContext(), llvm::cast<clang::AutoType>(qual_type)->getDeducedType()).
- GetFieldAtIndex (idx,
- name,
- bit_offset_ptr,
- bitfield_bit_size_ptr,
- is_bitfield_ptr);
-
- case clang::Type::Elaborated:
- return CompilerType (getASTContext(), llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType()).
- GetFieldAtIndex (idx,
- name,
- bit_offset_ptr,
- bitfield_bit_size_ptr,
- is_bitfield_ptr);
-
- case clang::Type::Paren:
- return CompilerType (getASTContext(), llvm::cast<clang::ParenType>(qual_type)->desugar()).
- GetFieldAtIndex (idx,
- name,
- bit_offset_ptr,
- bitfield_bit_size_ptr,
- is_bitfield_ptr);
-
- default:
- break;
- }
+CompilerType ClangASTContext::GetFieldAtIndex(lldb::opaque_compiler_type_t type,
+ size_t idx, std::string &name,
+ uint64_t *bit_offset_ptr,
+ uint32_t *bitfield_bit_size_ptr,
+ bool *is_bitfield_ptr) {
+ if (!type)
return CompilerType();
-}
-uint32_t
-ClangASTContext::GetNumDirectBaseClasses (lldb::opaque_compiler_type_t type)
-{
- uint32_t count = 0;
- clang::QualType qual_type(GetCanonicalQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Record:
- if (GetCompleteType(type))
- {
- const clang::CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
- if (cxx_record_decl)
- count = cxx_record_decl->getNumBases();
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Record:
+ if (GetCompleteType(type)) {
+ const clang::RecordType *record_type =
+ llvm::cast<clang::RecordType>(qual_type.getTypePtr());
+ const clang::RecordDecl *record_decl = record_type->getDecl();
+ uint32_t field_idx = 0;
+ clang::RecordDecl::field_iterator field, field_end;
+ for (field = record_decl->field_begin(),
+ field_end = record_decl->field_end();
+ field != field_end; ++field, ++field_idx) {
+ if (idx == field_idx) {
+ // Print the member type if requested
+ // Print the member name and equal sign
+ name.assign(field->getNameAsString());
+
+ // Figure out the type byte size (field_type_info.first) and
+ // alignment (field_type_info.second) from the AST context.
+ if (bit_offset_ptr) {
+ const clang::ASTRecordLayout &record_layout =
+ getASTContext()->getASTRecordLayout(record_decl);
+ *bit_offset_ptr = record_layout.getFieldOffset(field_idx);
+ }
+
+ const bool is_bitfield = field->isBitField();
+
+ if (bitfield_bit_size_ptr) {
+ *bitfield_bit_size_ptr = 0;
+
+ if (is_bitfield) {
+ clang::Expr *bitfield_bit_size_expr = field->getBitWidth();
+ llvm::APSInt bitfield_apsint;
+ if (bitfield_bit_size_expr &&
+ bitfield_bit_size_expr->EvaluateAsInt(bitfield_apsint,
+ *getASTContext())) {
+ *bitfield_bit_size_ptr = bitfield_apsint.getLimitedValue();
+ }
}
- break;
-
- case clang::Type::ObjCObjectPointer:
- count = GetPointeeType(type).GetNumDirectBaseClasses();
- break;
-
- case clang::Type::ObjCObject:
- if (GetCompleteType(type))
- {
- const clang::ObjCObjectType *objc_class_type = qual_type->getAsObjCQualifiedInterfaceType();
- if (objc_class_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
-
- if (class_interface_decl && class_interface_decl->getSuperClass())
- count = 1;
- }
- }
- break;
- case clang::Type::ObjCInterface:
- if (GetCompleteType(type))
- {
- const clang::ObjCInterfaceType *objc_interface_type = qual_type->getAs<clang::ObjCInterfaceType>();
- if (objc_interface_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_interface_type->getInterface();
-
- if (class_interface_decl && class_interface_decl->getSuperClass())
- count = 1;
- }
- }
- break;
-
-
- case clang::Type::Typedef:
- count = GetNumDirectBaseClasses(llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr());
- break;
-
- case clang::Type::Auto:
- count = GetNumDirectBaseClasses(llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr());
- break;
-
- case clang::Type::Elaborated:
- count = GetNumDirectBaseClasses(llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr());
- break;
-
- case clang::Type::Paren:
- return GetNumDirectBaseClasses(llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr());
-
- default:
- break;
- }
- return count;
+ }
+ if (is_bitfield_ptr)
+ *is_bitfield_ptr = is_bitfield;
+ return CompilerType(getASTContext(), field->getType());
+ }
+ }
+ }
+ break;
+
+ case clang::Type::ObjCObjectPointer:
+ if (GetCompleteType(type)) {
+ const clang::ObjCObjectPointerType *objc_class_type =
+ qual_type->getAsObjCInterfacePointerType();
+ if (objc_class_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterfaceDecl();
+ return CompilerType(
+ this, GetObjCFieldAtIndex(getASTContext(), class_interface_decl,
+ idx, name, bit_offset_ptr,
+ bitfield_bit_size_ptr, is_bitfield_ptr));
+ }
+ }
+ break;
+
+ case clang::Type::ObjCObject:
+ case clang::Type::ObjCInterface:
+ if (GetCompleteType(type)) {
+ const clang::ObjCObjectType *objc_class_type =
+ llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
+ assert(objc_class_type);
+ if (objc_class_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterface();
+ return CompilerType(
+ this, GetObjCFieldAtIndex(getASTContext(), class_interface_decl,
+ idx, name, bit_offset_ptr,
+ bitfield_bit_size_ptr, is_bitfield_ptr));
+ }
+ }
+ break;
+
+ case clang::Type::Typedef:
+ return CompilerType(getASTContext(),
+ llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType())
+ .GetFieldAtIndex(idx, name, bit_offset_ptr, bitfield_bit_size_ptr,
+ is_bitfield_ptr);
+
+ case clang::Type::Auto:
+ return CompilerType(
+ getASTContext(),
+ llvm::cast<clang::AutoType>(qual_type)->getDeducedType())
+ .GetFieldAtIndex(idx, name, bit_offset_ptr, bitfield_bit_size_ptr,
+ is_bitfield_ptr);
+
+ case clang::Type::Elaborated:
+ return CompilerType(
+ getASTContext(),
+ llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType())
+ .GetFieldAtIndex(idx, name, bit_offset_ptr, bitfield_bit_size_ptr,
+ is_bitfield_ptr);
+
+ case clang::Type::Paren:
+ return CompilerType(getASTContext(),
+ llvm::cast<clang::ParenType>(qual_type)->desugar())
+ .GetFieldAtIndex(idx, name, bit_offset_ptr, bitfield_bit_size_ptr,
+ is_bitfield_ptr);
+
+ default:
+ break;
+ }
+ return CompilerType();
}
uint32_t
-ClangASTContext::GetNumVirtualBaseClasses (lldb::opaque_compiler_type_t type)
-{
- uint32_t count = 0;
- clang::QualType qual_type(GetCanonicalQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Record:
- if (GetCompleteType(type))
- {
- const clang::CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
- if (cxx_record_decl)
- count = cxx_record_decl->getNumVBases();
- }
- break;
-
- case clang::Type::Typedef:
- count = GetNumVirtualBaseClasses(llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr());
- break;
-
- case clang::Type::Auto:
- count = GetNumVirtualBaseClasses(llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr());
- break;
-
- case clang::Type::Elaborated:
- count = GetNumVirtualBaseClasses(llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr());
- break;
-
- case clang::Type::Paren:
- count = GetNumVirtualBaseClasses(llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr());
- break;
-
- default:
- break;
- }
- return count;
-
+ClangASTContext::GetNumDirectBaseClasses(lldb::opaque_compiler_type_t type) {
+ uint32_t count = 0;
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Record:
+ if (GetCompleteType(type)) {
+ const clang::CXXRecordDecl *cxx_record_decl =
+ qual_type->getAsCXXRecordDecl();
+ if (cxx_record_decl)
+ count = cxx_record_decl->getNumBases();
+ }
+ break;
+
+ case clang::Type::ObjCObjectPointer:
+ count = GetPointeeType(type).GetNumDirectBaseClasses();
+ break;
+
+ case clang::Type::ObjCObject:
+ if (GetCompleteType(type)) {
+ const clang::ObjCObjectType *objc_class_type =
+ qual_type->getAsObjCQualifiedInterfaceType();
+ if (objc_class_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterface();
+
+ if (class_interface_decl && class_interface_decl->getSuperClass())
+ count = 1;
+ }
+ }
+ break;
+ case clang::Type::ObjCInterface:
+ if (GetCompleteType(type)) {
+ const clang::ObjCInterfaceType *objc_interface_type =
+ qual_type->getAs<clang::ObjCInterfaceType>();
+ if (objc_interface_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_interface_type->getInterface();
+
+ if (class_interface_decl && class_interface_decl->getSuperClass())
+ count = 1;
+ }
+ }
+ break;
+
+ case clang::Type::Typedef:
+ count = GetNumDirectBaseClasses(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr());
+ break;
+
+ case clang::Type::Auto:
+ count = GetNumDirectBaseClasses(llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr());
+ break;
+
+ case clang::Type::Elaborated:
+ count = GetNumDirectBaseClasses(llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr());
+ break;
+
+ case clang::Type::Paren:
+ return GetNumDirectBaseClasses(
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr());
+
+ default:
+ break;
+ }
+ return count;
}
-CompilerType
-ClangASTContext::GetDirectBaseClassAtIndex (lldb::opaque_compiler_type_t type, size_t idx, uint32_t *bit_offset_ptr)
-{
- clang::QualType qual_type(GetCanonicalQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Record:
- if (GetCompleteType(type))
- {
- const clang::CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
- if (cxx_record_decl)
- {
- uint32_t curr_idx = 0;
- clang::CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
- for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end();
- base_class != base_class_end;
- ++base_class, ++curr_idx)
- {
- if (curr_idx == idx)
- {
- if (bit_offset_ptr)
- {
- const clang::ASTRecordLayout &record_layout = getASTContext()->getASTRecordLayout(cxx_record_decl);
- const clang::CXXRecordDecl *base_class_decl = llvm::cast<clang::CXXRecordDecl>(base_class->getType()->getAs<clang::RecordType>()->getDecl());
- if (base_class->isVirtual())
- *bit_offset_ptr = record_layout.getVBaseClassOffset(base_class_decl).getQuantity() * 8;
- else
- *bit_offset_ptr = record_layout.getBaseClassOffset(base_class_decl).getQuantity() * 8;
- }
- return CompilerType (this, base_class->getType().getAsOpaquePtr());
- }
- }
- }
- }
- break;
-
- case clang::Type::ObjCObjectPointer:
- return GetPointeeType(type).GetDirectBaseClassAtIndex(idx, bit_offset_ptr);
-
- case clang::Type::ObjCObject:
- if (idx == 0 && GetCompleteType(type))
- {
- const clang::ObjCObjectType *objc_class_type = qual_type->getAsObjCQualifiedInterfaceType();
- if (objc_class_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
-
- if (class_interface_decl)
- {
- clang::ObjCInterfaceDecl *superclass_interface_decl = class_interface_decl->getSuperClass();
- if (superclass_interface_decl)
- {
- if (bit_offset_ptr)
- *bit_offset_ptr = 0;
- return CompilerType (getASTContext(), getASTContext()->getObjCInterfaceType(superclass_interface_decl));
- }
- }
- }
+uint32_t
+ClangASTContext::GetNumVirtualBaseClasses(lldb::opaque_compiler_type_t type) {
+ uint32_t count = 0;
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Record:
+ if (GetCompleteType(type)) {
+ const clang::CXXRecordDecl *cxx_record_decl =
+ qual_type->getAsCXXRecordDecl();
+ if (cxx_record_decl)
+ count = cxx_record_decl->getNumVBases();
+ }
+ break;
+
+ case clang::Type::Typedef:
+ count = GetNumVirtualBaseClasses(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr());
+ break;
+
+ case clang::Type::Auto:
+ count = GetNumVirtualBaseClasses(llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr());
+ break;
+
+ case clang::Type::Elaborated:
+ count =
+ GetNumVirtualBaseClasses(llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr());
+ break;
+
+ case clang::Type::Paren:
+ count = GetNumVirtualBaseClasses(
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr());
+ break;
+
+ default:
+ break;
+ }
+ return count;
+}
+
+CompilerType ClangASTContext::GetDirectBaseClassAtIndex(
+ lldb::opaque_compiler_type_t type, size_t idx, uint32_t *bit_offset_ptr) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Record:
+ if (GetCompleteType(type)) {
+ const clang::CXXRecordDecl *cxx_record_decl =
+ qual_type->getAsCXXRecordDecl();
+ if (cxx_record_decl) {
+ uint32_t curr_idx = 0;
+ clang::CXXRecordDecl::base_class_const_iterator base_class,
+ base_class_end;
+ for (base_class = cxx_record_decl->bases_begin(),
+ base_class_end = cxx_record_decl->bases_end();
+ base_class != base_class_end; ++base_class, ++curr_idx) {
+ if (curr_idx == idx) {
+ if (bit_offset_ptr) {
+ const clang::ASTRecordLayout &record_layout =
+ getASTContext()->getASTRecordLayout(cxx_record_decl);
+ const clang::CXXRecordDecl *base_class_decl =
+ llvm::cast<clang::CXXRecordDecl>(
+ base_class->getType()
+ ->getAs<clang::RecordType>()
+ ->getDecl());
+ if (base_class->isVirtual())
+ *bit_offset_ptr =
+ record_layout.getVBaseClassOffset(base_class_decl)
+ .getQuantity() *
+ 8;
+ else
+ *bit_offset_ptr =
+ record_layout.getBaseClassOffset(base_class_decl)
+ .getQuantity() *
+ 8;
}
- break;
- case clang::Type::ObjCInterface:
- if (idx == 0 && GetCompleteType(type))
- {
- const clang::ObjCObjectType *objc_interface_type = qual_type->getAs<clang::ObjCInterfaceType>();
- if (objc_interface_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_interface_type->getInterface();
-
- if (class_interface_decl)
- {
- clang::ObjCInterfaceDecl *superclass_interface_decl = class_interface_decl->getSuperClass();
- if (superclass_interface_decl)
- {
- if (bit_offset_ptr)
- *bit_offset_ptr = 0;
- return CompilerType (getASTContext(), getASTContext()->getObjCInterfaceType(superclass_interface_decl));
- }
- }
- }
+ return CompilerType(this, base_class->getType().getAsOpaquePtr());
+ }
+ }
+ }
+ }
+ break;
+
+ case clang::Type::ObjCObjectPointer:
+ return GetPointeeType(type).GetDirectBaseClassAtIndex(idx, bit_offset_ptr);
+
+ case clang::Type::ObjCObject:
+ if (idx == 0 && GetCompleteType(type)) {
+ const clang::ObjCObjectType *objc_class_type =
+ qual_type->getAsObjCQualifiedInterfaceType();
+ if (objc_class_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterface();
+
+ if (class_interface_decl) {
+ clang::ObjCInterfaceDecl *superclass_interface_decl =
+ class_interface_decl->getSuperClass();
+ if (superclass_interface_decl) {
+ if (bit_offset_ptr)
+ *bit_offset_ptr = 0;
+ return CompilerType(getASTContext(),
+ getASTContext()->getObjCInterfaceType(
+ superclass_interface_decl));
+ }
+ }
+ }
+ }
+ break;
+ case clang::Type::ObjCInterface:
+ if (idx == 0 && GetCompleteType(type)) {
+ const clang::ObjCObjectType *objc_interface_type =
+ qual_type->getAs<clang::ObjCInterfaceType>();
+ if (objc_interface_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_interface_type->getInterface();
+
+ if (class_interface_decl) {
+ clang::ObjCInterfaceDecl *superclass_interface_decl =
+ class_interface_decl->getSuperClass();
+ if (superclass_interface_decl) {
+ if (bit_offset_ptr)
+ *bit_offset_ptr = 0;
+ return CompilerType(getASTContext(),
+ getASTContext()->getObjCInterfaceType(
+ superclass_interface_decl));
+ }
+ }
+ }
+ }
+ break;
+
+ case clang::Type::Typedef:
+ return GetDirectBaseClassAtIndex(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr(),
+ idx, bit_offset_ptr);
+
+ case clang::Type::Auto:
+ return GetDirectBaseClassAtIndex(llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr(),
+ idx, bit_offset_ptr);
+
+ case clang::Type::Elaborated:
+ return GetDirectBaseClassAtIndex(
+ llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr(),
+ idx, bit_offset_ptr);
+
+ case clang::Type::Paren:
+ return GetDirectBaseClassAtIndex(
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(),
+ idx, bit_offset_ptr);
+
+ default:
+ break;
+ }
+ return CompilerType();
+}
+
+CompilerType ClangASTContext::GetVirtualBaseClassAtIndex(
+ lldb::opaque_compiler_type_t type, size_t idx, uint32_t *bit_offset_ptr) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Record:
+ if (GetCompleteType(type)) {
+ const clang::CXXRecordDecl *cxx_record_decl =
+ qual_type->getAsCXXRecordDecl();
+ if (cxx_record_decl) {
+ uint32_t curr_idx = 0;
+ clang::CXXRecordDecl::base_class_const_iterator base_class,
+ base_class_end;
+ for (base_class = cxx_record_decl->vbases_begin(),
+ base_class_end = cxx_record_decl->vbases_end();
+ base_class != base_class_end; ++base_class, ++curr_idx) {
+ if (curr_idx == idx) {
+ if (bit_offset_ptr) {
+ const clang::ASTRecordLayout &record_layout =
+ getASTContext()->getASTRecordLayout(cxx_record_decl);
+ const clang::CXXRecordDecl *base_class_decl =
+ llvm::cast<clang::CXXRecordDecl>(
+ base_class->getType()
+ ->getAs<clang::RecordType>()
+ ->getDecl());
+ *bit_offset_ptr =
+ record_layout.getVBaseClassOffset(base_class_decl)
+ .getQuantity() *
+ 8;
}
- break;
-
-
- case clang::Type::Typedef:
- return GetDirectBaseClassAtIndex (llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(), idx, bit_offset_ptr);
-
- case clang::Type::Auto:
- return GetDirectBaseClassAtIndex (llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr(), idx, bit_offset_ptr);
-
- case clang::Type::Elaborated:
- return GetDirectBaseClassAtIndex (llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr(), idx, bit_offset_ptr);
-
- case clang::Type::Paren:
- return GetDirectBaseClassAtIndex (llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(), idx, bit_offset_ptr);
-
- default:
- break;
+ return CompilerType(this, base_class->getType().getAsOpaquePtr());
+ }
+ }
+ }
}
- return CompilerType();
-}
+ break;
-CompilerType
-ClangASTContext::GetVirtualBaseClassAtIndex (lldb::opaque_compiler_type_t type,
- size_t idx,
- uint32_t *bit_offset_ptr)
-{
- clang::QualType qual_type(GetCanonicalQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Record:
- if (GetCompleteType(type))
- {
- const clang::CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
- if (cxx_record_decl)
- {
- uint32_t curr_idx = 0;
- clang::CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
- for (base_class = cxx_record_decl->vbases_begin(), base_class_end = cxx_record_decl->vbases_end();
- base_class != base_class_end;
- ++base_class, ++curr_idx)
- {
- if (curr_idx == idx)
- {
- if (bit_offset_ptr)
- {
- const clang::ASTRecordLayout &record_layout = getASTContext()->getASTRecordLayout(cxx_record_decl);
- const clang::CXXRecordDecl *base_class_decl = llvm::cast<clang::CXXRecordDecl>(base_class->getType()->getAs<clang::RecordType>()->getDecl());
- *bit_offset_ptr = record_layout.getVBaseClassOffset(base_class_decl).getQuantity() * 8;
+ case clang::Type::Typedef:
+ return GetVirtualBaseClassAtIndex(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr(),
+ idx, bit_offset_ptr);
- }
- return CompilerType (this, base_class->getType().getAsOpaquePtr());
- }
- }
- }
- }
- break;
+ case clang::Type::Auto:
+ return GetVirtualBaseClassAtIndex(llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr(),
+ idx, bit_offset_ptr);
- case clang::Type::Typedef:
- return GetVirtualBaseClassAtIndex (llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(), idx, bit_offset_ptr);
-
- case clang::Type::Auto:
- return GetVirtualBaseClassAtIndex (llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr(), idx, bit_offset_ptr);
-
- case clang::Type::Elaborated:
- return GetVirtualBaseClassAtIndex (llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr(), idx, bit_offset_ptr);
+ case clang::Type::Elaborated:
+ return GetVirtualBaseClassAtIndex(
+ llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr(),
+ idx, bit_offset_ptr);
- case clang::Type::Paren:
- return GetVirtualBaseClassAtIndex(llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(), idx,
- bit_offset_ptr);
-
- default:
- break;
- }
- return CompilerType();
+ case clang::Type::Paren:
+ return GetVirtualBaseClassAtIndex(
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(),
+ idx, bit_offset_ptr);
+ default:
+ break;
+ }
+ return CompilerType();
}
// If a pointer to a pointee type (the clang_type arg) says that it has no
@@ -6250,776 +6156,757 @@ ClangASTContext::GetVirtualBaseClassAtIndex (lldb::opaque_compiler_type_t type,
// different result. For example, an "int *" has one child that is an integer,
// but a function pointer doesn't have any children. Likewise if a Record type
// claims it has no children, then there really is nothing to show.
-uint32_t
-ClangASTContext::GetNumPointeeChildren (clang::QualType type)
-{
- if (type.isNull())
- return 0;
-
- clang::QualType qual_type(type.getCanonicalType());
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Builtin:
- switch (llvm::cast<clang::BuiltinType>(qual_type)->getKind())
- {
- case clang::BuiltinType::UnknownAny:
- case clang::BuiltinType::Void:
- case clang::BuiltinType::NullPtr:
- case clang::BuiltinType::OCLEvent:
- case clang::BuiltinType::OCLImage1dRO:
- case clang::BuiltinType::OCLImage1dWO:
- case clang::BuiltinType::OCLImage1dRW:
- case clang::BuiltinType::OCLImage1dArrayRO:
- case clang::BuiltinType::OCLImage1dArrayWO:
- case clang::BuiltinType::OCLImage1dArrayRW:
- case clang::BuiltinType::OCLImage1dBufferRO:
- case clang::BuiltinType::OCLImage1dBufferWO:
- case clang::BuiltinType::OCLImage1dBufferRW:
- case clang::BuiltinType::OCLImage2dRO:
- case clang::BuiltinType::OCLImage2dWO:
- case clang::BuiltinType::OCLImage2dRW:
- case clang::BuiltinType::OCLImage2dArrayRO:
- case clang::BuiltinType::OCLImage2dArrayWO:
- case clang::BuiltinType::OCLImage2dArrayRW:
- case clang::BuiltinType::OCLImage3dRO:
- case clang::BuiltinType::OCLImage3dWO:
- case clang::BuiltinType::OCLImage3dRW:
- case clang::BuiltinType::OCLSampler:
- return 0;
- case clang::BuiltinType::Bool:
- case clang::BuiltinType::Char_U:
- case clang::BuiltinType::UChar:
- case clang::BuiltinType::WChar_U:
- case clang::BuiltinType::Char16:
- case clang::BuiltinType::Char32:
- case clang::BuiltinType::UShort:
- case clang::BuiltinType::UInt:
- case clang::BuiltinType::ULong:
- case clang::BuiltinType::ULongLong:
- case clang::BuiltinType::UInt128:
- case clang::BuiltinType::Char_S:
- case clang::BuiltinType::SChar:
- case clang::BuiltinType::WChar_S:
- case clang::BuiltinType::Short:
- case clang::BuiltinType::Int:
- case clang::BuiltinType::Long:
- case clang::BuiltinType::LongLong:
- case clang::BuiltinType::Int128:
- case clang::BuiltinType::Float:
- case clang::BuiltinType::Double:
- case clang::BuiltinType::LongDouble:
- case clang::BuiltinType::Dependent:
- case clang::BuiltinType::Overload:
- case clang::BuiltinType::ObjCId:
- case clang::BuiltinType::ObjCClass:
- case clang::BuiltinType::ObjCSel:
- case clang::BuiltinType::BoundMember:
- case clang::BuiltinType::Half:
- case clang::BuiltinType::ARCUnbridgedCast:
- case clang::BuiltinType::PseudoObject:
- case clang::BuiltinType::BuiltinFn:
- case clang::BuiltinType::OMPArraySection:
- return 1;
- default:
- return 0;
- }
- break;
-
- case clang::Type::Complex: return 1;
- case clang::Type::Pointer: return 1;
- case clang::Type::BlockPointer: return 0; // If block pointers don't have debug info, then no children for them
- case clang::Type::LValueReference: return 1;
- case clang::Type::RValueReference: return 1;
- case clang::Type::MemberPointer: return 0;
- case clang::Type::ConstantArray: return 0;
- case clang::Type::IncompleteArray: return 0;
- case clang::Type::VariableArray: return 0;
- case clang::Type::DependentSizedArray: return 0;
- case clang::Type::DependentSizedExtVector: return 0;
- case clang::Type::Vector: return 0;
- case clang::Type::ExtVector: return 0;
- case clang::Type::FunctionProto: return 0; // When we function pointers, they have no children...
- case clang::Type::FunctionNoProto: return 0; // When we function pointers, they have no children...
- case clang::Type::UnresolvedUsing: return 0;
- case clang::Type::Paren: return GetNumPointeeChildren (llvm::cast<clang::ParenType>(qual_type)->desugar());
- case clang::Type::Typedef: return GetNumPointeeChildren (llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType());
- case clang::Type::Auto: return GetNumPointeeChildren (llvm::cast<clang::AutoType>(qual_type)->getDeducedType());
- case clang::Type::Elaborated: return GetNumPointeeChildren (llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType());
- case clang::Type::TypeOfExpr: return 0;
- case clang::Type::TypeOf: return 0;
- case clang::Type::Decltype: return 0;
- case clang::Type::Record: return 0;
- case clang::Type::Enum: return 1;
- case clang::Type::TemplateTypeParm: return 1;
- case clang::Type::SubstTemplateTypeParm: return 1;
- case clang::Type::TemplateSpecialization: return 1;
- case clang::Type::InjectedClassName: return 0;
- case clang::Type::DependentName: return 1;
- case clang::Type::DependentTemplateSpecialization: return 1;
- case clang::Type::ObjCObject: return 0;
- case clang::Type::ObjCInterface: return 0;
- case clang::Type::ObjCObjectPointer: return 1;
- default:
- break;
- }
+uint32_t ClangASTContext::GetNumPointeeChildren(clang::QualType type) {
+ if (type.isNull())
return 0;
-}
+ clang::QualType qual_type(type.getCanonicalType());
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Builtin:
+ switch (llvm::cast<clang::BuiltinType>(qual_type)->getKind()) {
+ case clang::BuiltinType::UnknownAny:
+ case clang::BuiltinType::Void:
+ case clang::BuiltinType::NullPtr:
+ case clang::BuiltinType::OCLEvent:
+ case clang::BuiltinType::OCLImage1dRO:
+ case clang::BuiltinType::OCLImage1dWO:
+ case clang::BuiltinType::OCLImage1dRW:
+ case clang::BuiltinType::OCLImage1dArrayRO:
+ case clang::BuiltinType::OCLImage1dArrayWO:
+ case clang::BuiltinType::OCLImage1dArrayRW:
+ case clang::BuiltinType::OCLImage1dBufferRO:
+ case clang::BuiltinType::OCLImage1dBufferWO:
+ case clang::BuiltinType::OCLImage1dBufferRW:
+ case clang::BuiltinType::OCLImage2dRO:
+ case clang::BuiltinType::OCLImage2dWO:
+ case clang::BuiltinType::OCLImage2dRW:
+ case clang::BuiltinType::OCLImage2dArrayRO:
+ case clang::BuiltinType::OCLImage2dArrayWO:
+ case clang::BuiltinType::OCLImage2dArrayRW:
+ case clang::BuiltinType::OCLImage3dRO:
+ case clang::BuiltinType::OCLImage3dWO:
+ case clang::BuiltinType::OCLImage3dRW:
+ case clang::BuiltinType::OCLSampler:
+ return 0;
+ case clang::BuiltinType::Bool:
+ case clang::BuiltinType::Char_U:
+ case clang::BuiltinType::UChar:
+ case clang::BuiltinType::WChar_U:
+ case clang::BuiltinType::Char16:
+ case clang::BuiltinType::Char32:
+ case clang::BuiltinType::UShort:
+ case clang::BuiltinType::UInt:
+ case clang::BuiltinType::ULong:
+ case clang::BuiltinType::ULongLong:
+ case clang::BuiltinType::UInt128:
+ case clang::BuiltinType::Char_S:
+ case clang::BuiltinType::SChar:
+ case clang::BuiltinType::WChar_S:
+ case clang::BuiltinType::Short:
+ case clang::BuiltinType::Int:
+ case clang::BuiltinType::Long:
+ case clang::BuiltinType::LongLong:
+ case clang::BuiltinType::Int128:
+ case clang::BuiltinType::Float:
+ case clang::BuiltinType::Double:
+ case clang::BuiltinType::LongDouble:
+ case clang::BuiltinType::Dependent:
+ case clang::BuiltinType::Overload:
+ case clang::BuiltinType::ObjCId:
+ case clang::BuiltinType::ObjCClass:
+ case clang::BuiltinType::ObjCSel:
+ case clang::BuiltinType::BoundMember:
+ case clang::BuiltinType::Half:
+ case clang::BuiltinType::ARCUnbridgedCast:
+ case clang::BuiltinType::PseudoObject:
+ case clang::BuiltinType::BuiltinFn:
+ case clang::BuiltinType::OMPArraySection:
+ return 1;
+ default:
+ return 0;
+ }
+ break;
-CompilerType
-ClangASTContext::GetChildCompilerTypeAtIndex (lldb::opaque_compiler_type_t type,
- ExecutionContext *exe_ctx,
- size_t idx,
- bool transparent_pointers,
- bool omit_empty_base_classes,
- bool ignore_array_bounds,
- std::string& child_name,
- uint32_t &child_byte_size,
- int32_t &child_byte_offset,
- uint32_t &child_bitfield_bit_size,
- uint32_t &child_bitfield_bit_offset,
- bool &child_is_base_class,
- bool &child_is_deref_of_parent,
- ValueObject *valobj,
- uint64_t &language_flags)
-{
- if (!type)
- return CompilerType();
-
- clang::QualType parent_qual_type(GetCanonicalQualType(type));
- const clang::Type::TypeClass parent_type_class = parent_qual_type->getTypeClass();
- child_bitfield_bit_size = 0;
- child_bitfield_bit_offset = 0;
- child_is_base_class = false;
- language_flags = 0;
-
- const bool idx_is_valid = idx < GetNumChildren (type, omit_empty_base_classes);
- uint32_t bit_offset;
- switch (parent_type_class)
- {
- case clang::Type::Builtin:
- if (idx_is_valid)
- {
- switch (llvm::cast<clang::BuiltinType>(parent_qual_type)->getKind())
- {
- case clang::BuiltinType::ObjCId:
- case clang::BuiltinType::ObjCClass:
- child_name = "isa";
- child_byte_size = getASTContext()->getTypeSize(getASTContext()->ObjCBuiltinClassTy) / CHAR_BIT;
- return CompilerType (getASTContext(), getASTContext()->ObjCBuiltinClassTy);
-
- default:
- break;
- }
- }
- break;
-
- case clang::Type::Record:
- if (idx_is_valid && GetCompleteType(type))
- {
- const clang::RecordType *record_type = llvm::cast<clang::RecordType>(parent_qual_type.getTypePtr());
- const clang::RecordDecl *record_decl = record_type->getDecl();
- assert(record_decl);
- const clang::ASTRecordLayout &record_layout = getASTContext()->getASTRecordLayout(record_decl);
- uint32_t child_idx = 0;
-
- const clang::CXXRecordDecl *cxx_record_decl = llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
- if (cxx_record_decl)
- {
- // We might have base classes to print out first
- clang::CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
- for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end();
- base_class != base_class_end;
- ++base_class)
- {
- const clang::CXXRecordDecl *base_class_decl = nullptr;
-
- // Skip empty base classes
- if (omit_empty_base_classes)
- {
- base_class_decl = llvm::cast<clang::CXXRecordDecl>(base_class->getType()->getAs<clang::RecordType>()->getDecl());
- if (ClangASTContext::RecordHasFields(base_class_decl) == false)
- continue;
- }
-
- if (idx == child_idx)
- {
- if (base_class_decl == nullptr)
- base_class_decl = llvm::cast<clang::CXXRecordDecl>(base_class->getType()->getAs<clang::RecordType>()->getDecl());
-
-
- if (base_class->isVirtual())
- {
- bool handled = false;
- if (valobj)
- {
- Error err;
- AddressType addr_type = eAddressTypeInvalid;
- lldb::addr_t vtable_ptr_addr = valobj->GetCPPVTableAddress(addr_type);
-
- if (vtable_ptr_addr != LLDB_INVALID_ADDRESS && addr_type == eAddressTypeLoad)
- {
-
- ExecutionContext exe_ctx (valobj->GetExecutionContextRef());
- Process *process = exe_ctx.GetProcessPtr();
- if (process)
- {
- clang::VTableContextBase *vtable_ctx = getASTContext()->getVTableContext();
- if (vtable_ctx)
- {
- if (vtable_ctx->isMicrosoft())
- {
- clang::MicrosoftVTableContext *msoft_vtable_ctx = static_cast<clang::MicrosoftVTableContext *>(vtable_ctx);
-
- if (vtable_ptr_addr)
- {
- const lldb::addr_t vbtable_ptr_addr = vtable_ptr_addr + record_layout.getVBPtrOffset().getQuantity();
-
- const lldb::addr_t vbtable_ptr = process->ReadPointerFromMemory(vbtable_ptr_addr, err);
- if (vbtable_ptr != LLDB_INVALID_ADDRESS)
- {
- // Get the index into the virtual base table. The index is the index in uint32_t from vbtable_ptr
- const unsigned vbtable_index = msoft_vtable_ctx->getVBTableIndex(cxx_record_decl, base_class_decl);
- const lldb::addr_t base_offset_addr = vbtable_ptr + vbtable_index * 4;
- const uint32_t base_offset = process->ReadUnsignedIntegerFromMemory(base_offset_addr, 4, UINT32_MAX, err);
- if (base_offset != UINT32_MAX)
- {
- handled = true;
- bit_offset = base_offset * 8;
- }
- }
- }
- }
- else
- {
- clang::ItaniumVTableContext *itanium_vtable_ctx = static_cast<clang::ItaniumVTableContext *>(vtable_ctx);
- if (vtable_ptr_addr)
- {
- const lldb::addr_t vtable_ptr = process->ReadPointerFromMemory(vtable_ptr_addr, err);
- if (vtable_ptr != LLDB_INVALID_ADDRESS)
- {
- clang::CharUnits base_offset_offset = itanium_vtable_ctx->getVirtualBaseOffsetOffset(cxx_record_decl, base_class_decl);
- const lldb::addr_t base_offset_addr = vtable_ptr + base_offset_offset.getQuantity();
- const uint32_t base_offset_size = process->GetAddressByteSize();
- const uint64_t base_offset = process->ReadUnsignedIntegerFromMemory(base_offset_addr, base_offset_size, UINT32_MAX, err);
- if (base_offset < UINT32_MAX)
- {
- handled = true;
- bit_offset = base_offset * 8;
- }
- }
- }
- }
- }
- }
- }
-
- }
- if (!handled)
- bit_offset = record_layout.getVBaseClassOffset(base_class_decl).getQuantity() * 8;
- }
- else
- bit_offset = record_layout.getBaseClassOffset(base_class_decl).getQuantity() * 8;
-
- // Base classes should be a multiple of 8 bits in size
- child_byte_offset = bit_offset/8;
- CompilerType base_class_clang_type(getASTContext(), base_class->getType());
- child_name = base_class_clang_type.GetTypeName().AsCString("");
- uint64_t base_class_clang_type_bit_size = base_class_clang_type.GetBitSize(exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
-
- // Base classes bit sizes should be a multiple of 8 bits in size
- assert (base_class_clang_type_bit_size % 8 == 0);
- child_byte_size = base_class_clang_type_bit_size / 8;
- child_is_base_class = true;
- return base_class_clang_type;
- }
- // We don't increment the child index in the for loop since we might
- // be skipping empty base classes
- ++child_idx;
- }
- }
- // Make sure index is in range...
- uint32_t field_idx = 0;
- clang::RecordDecl::field_iterator field, field_end;
- for (field = record_decl->field_begin(), field_end = record_decl->field_end(); field != field_end; ++field, ++field_idx, ++child_idx)
- {
- if (idx == child_idx)
- {
- // Print the member type if requested
- // Print the member name and equal sign
- child_name.assign(field->getNameAsString().c_str());
-
- // Figure out the type byte size (field_type_info.first) and
- // alignment (field_type_info.second) from the AST context.
- CompilerType field_clang_type (getASTContext(), field->getType());
- assert(field_idx < record_layout.getFieldCount());
- child_byte_size = field_clang_type.GetByteSize(exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
- const uint32_t child_bit_size = child_byte_size * 8;
-
- // Figure out the field offset within the current struct/union/class type
- bit_offset = record_layout.getFieldOffset (field_idx);
- if (ClangASTContext::FieldIsBitfield (getASTContext(), *field, child_bitfield_bit_size))
- {
- child_bitfield_bit_offset = bit_offset % child_bit_size;
- const uint32_t child_bit_offset = bit_offset - child_bitfield_bit_offset;
- child_byte_offset = child_bit_offset / 8;
- }
- else
- {
- child_byte_offset = bit_offset / 8;
- }
-
- return field_clang_type;
- }
- }
- }
- break;
-
- case clang::Type::ObjCObject:
- case clang::Type::ObjCInterface:
- if (idx_is_valid && GetCompleteType(type))
- {
- const clang::ObjCObjectType *objc_class_type = llvm::dyn_cast<clang::ObjCObjectType>(parent_qual_type.getTypePtr());
- assert (objc_class_type);
- if (objc_class_type)
- {
- uint32_t child_idx = 0;
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
-
- if (class_interface_decl)
- {
-
- const clang::ASTRecordLayout &interface_layout = getASTContext()->getASTObjCInterfaceLayout(class_interface_decl);
- clang::ObjCInterfaceDecl *superclass_interface_decl = class_interface_decl->getSuperClass();
- if (superclass_interface_decl)
- {
- if (omit_empty_base_classes)
- {
- CompilerType base_class_clang_type (getASTContext(), getASTContext()->getObjCInterfaceType(superclass_interface_decl));
- if (base_class_clang_type.GetNumChildren(omit_empty_base_classes) > 0)
- {
- if (idx == 0)
- {
- clang::QualType ivar_qual_type(getASTContext()->getObjCInterfaceType(superclass_interface_decl));
-
-
- child_name.assign(superclass_interface_decl->getNameAsString().c_str());
-
- clang::TypeInfo ivar_type_info = getASTContext()->getTypeInfo(ivar_qual_type.getTypePtr());
-
- child_byte_size = ivar_type_info.Width / 8;
- child_byte_offset = 0;
- child_is_base_class = true;
-
- return CompilerType (getASTContext(), ivar_qual_type);
- }
-
- ++child_idx;
- }
+ case clang::Type::Complex:
+ return 1;
+ case clang::Type::Pointer:
+ return 1;
+ case clang::Type::BlockPointer:
+ return 0; // If block pointers don't have debug info, then no children for
+ // them
+ case clang::Type::LValueReference:
+ return 1;
+ case clang::Type::RValueReference:
+ return 1;
+ case clang::Type::MemberPointer:
+ return 0;
+ case clang::Type::ConstantArray:
+ return 0;
+ case clang::Type::IncompleteArray:
+ return 0;
+ case clang::Type::VariableArray:
+ return 0;
+ case clang::Type::DependentSizedArray:
+ return 0;
+ case clang::Type::DependentSizedExtVector:
+ return 0;
+ case clang::Type::Vector:
+ return 0;
+ case clang::Type::ExtVector:
+ return 0;
+ case clang::Type::FunctionProto:
+ return 0; // When we function pointers, they have no children...
+ case clang::Type::FunctionNoProto:
+ return 0; // When we function pointers, they have no children...
+ case clang::Type::UnresolvedUsing:
+ return 0;
+ case clang::Type::Paren:
+ return GetNumPointeeChildren(
+ llvm::cast<clang::ParenType>(qual_type)->desugar());
+ case clang::Type::Typedef:
+ return GetNumPointeeChildren(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType());
+ case clang::Type::Auto:
+ return GetNumPointeeChildren(
+ llvm::cast<clang::AutoType>(qual_type)->getDeducedType());
+ case clang::Type::Elaborated:
+ return GetNumPointeeChildren(
+ llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType());
+ case clang::Type::TypeOfExpr:
+ return 0;
+ case clang::Type::TypeOf:
+ return 0;
+ case clang::Type::Decltype:
+ return 0;
+ case clang::Type::Record:
+ return 0;
+ case clang::Type::Enum:
+ return 1;
+ case clang::Type::TemplateTypeParm:
+ return 1;
+ case clang::Type::SubstTemplateTypeParm:
+ return 1;
+ case clang::Type::TemplateSpecialization:
+ return 1;
+ case clang::Type::InjectedClassName:
+ return 0;
+ case clang::Type::DependentName:
+ return 1;
+ case clang::Type::DependentTemplateSpecialization:
+ return 1;
+ case clang::Type::ObjCObject:
+ return 0;
+ case clang::Type::ObjCInterface:
+ return 0;
+ case clang::Type::ObjCObjectPointer:
+ return 1;
+ default:
+ break;
+ }
+ return 0;
+}
+
+CompilerType ClangASTContext::GetChildCompilerTypeAtIndex(
+ lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx, size_t idx,
+ bool transparent_pointers, bool omit_empty_base_classes,
+ bool ignore_array_bounds, std::string &child_name,
+ uint32_t &child_byte_size, int32_t &child_byte_offset,
+ uint32_t &child_bitfield_bit_size, uint32_t &child_bitfield_bit_offset,
+ bool &child_is_base_class, bool &child_is_deref_of_parent,
+ ValueObject *valobj, uint64_t &language_flags) {
+ if (!type)
+ return CompilerType();
+
+ clang::QualType parent_qual_type(GetCanonicalQualType(type));
+ const clang::Type::TypeClass parent_type_class =
+ parent_qual_type->getTypeClass();
+ child_bitfield_bit_size = 0;
+ child_bitfield_bit_offset = 0;
+ child_is_base_class = false;
+ language_flags = 0;
+
+ const bool idx_is_valid = idx < GetNumChildren(type, omit_empty_base_classes);
+ uint32_t bit_offset;
+ switch (parent_type_class) {
+ case clang::Type::Builtin:
+ if (idx_is_valid) {
+ switch (llvm::cast<clang::BuiltinType>(parent_qual_type)->getKind()) {
+ case clang::BuiltinType::ObjCId:
+ case clang::BuiltinType::ObjCClass:
+ child_name = "isa";
+ child_byte_size =
+ getASTContext()->getTypeSize(getASTContext()->ObjCBuiltinClassTy) /
+ CHAR_BIT;
+ return CompilerType(getASTContext(),
+ getASTContext()->ObjCBuiltinClassTy);
+
+ default:
+ break;
+ }
+ }
+ break;
+
+ case clang::Type::Record:
+ if (idx_is_valid && GetCompleteType(type)) {
+ const clang::RecordType *record_type =
+ llvm::cast<clang::RecordType>(parent_qual_type.getTypePtr());
+ const clang::RecordDecl *record_decl = record_type->getDecl();
+ assert(record_decl);
+ const clang::ASTRecordLayout &record_layout =
+ getASTContext()->getASTRecordLayout(record_decl);
+ uint32_t child_idx = 0;
+
+ const clang::CXXRecordDecl *cxx_record_decl =
+ llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
+ if (cxx_record_decl) {
+ // We might have base classes to print out first
+ clang::CXXRecordDecl::base_class_const_iterator base_class,
+ base_class_end;
+ for (base_class = cxx_record_decl->bases_begin(),
+ base_class_end = cxx_record_decl->bases_end();
+ base_class != base_class_end; ++base_class) {
+ const clang::CXXRecordDecl *base_class_decl = nullptr;
+
+ // Skip empty base classes
+ if (omit_empty_base_classes) {
+ base_class_decl = llvm::cast<clang::CXXRecordDecl>(
+ base_class->getType()->getAs<clang::RecordType>()->getDecl());
+ if (ClangASTContext::RecordHasFields(base_class_decl) == false)
+ continue;
+ }
+
+ if (idx == child_idx) {
+ if (base_class_decl == nullptr)
+ base_class_decl = llvm::cast<clang::CXXRecordDecl>(
+ base_class->getType()->getAs<clang::RecordType>()->getDecl());
+
+ if (base_class->isVirtual()) {
+ bool handled = false;
+ if (valobj) {
+ Error err;
+ AddressType addr_type = eAddressTypeInvalid;
+ lldb::addr_t vtable_ptr_addr =
+ valobj->GetCPPVTableAddress(addr_type);
+
+ if (vtable_ptr_addr != LLDB_INVALID_ADDRESS &&
+ addr_type == eAddressTypeLoad) {
+
+ ExecutionContext exe_ctx(valobj->GetExecutionContextRef());
+ Process *process = exe_ctx.GetProcessPtr();
+ if (process) {
+ clang::VTableContextBase *vtable_ctx =
+ getASTContext()->getVTableContext();
+ if (vtable_ctx) {
+ if (vtable_ctx->isMicrosoft()) {
+ clang::MicrosoftVTableContext *msoft_vtable_ctx =
+ static_cast<clang::MicrosoftVTableContext *>(
+ vtable_ctx);
+
+ if (vtable_ptr_addr) {
+ const lldb::addr_t vbtable_ptr_addr =
+ vtable_ptr_addr +
+ record_layout.getVBPtrOffset().getQuantity();
+
+ const lldb::addr_t vbtable_ptr =
+ process->ReadPointerFromMemory(vbtable_ptr_addr,
+ err);
+ if (vbtable_ptr != LLDB_INVALID_ADDRESS) {
+ // Get the index into the virtual base table. The
+ // index is the index in uint32_t from vbtable_ptr
+ const unsigned vbtable_index =
+ msoft_vtable_ctx->getVBTableIndex(
+ cxx_record_decl, base_class_decl);
+ const lldb::addr_t base_offset_addr =
+ vbtable_ptr + vbtable_index * 4;
+ const uint32_t base_offset =
+ process->ReadUnsignedIntegerFromMemory(
+ base_offset_addr, 4, UINT32_MAX, err);
+ if (base_offset != UINT32_MAX) {
+ handled = true;
+ bit_offset = base_offset * 8;
}
- else
- ++child_idx;
+ }
}
-
- const uint32_t superclass_idx = child_idx;
-
- if (idx < (child_idx + class_interface_decl->ivar_size()))
- {
- clang::ObjCInterfaceDecl::ivar_iterator ivar_pos, ivar_end = class_interface_decl->ivar_end();
-
- for (ivar_pos = class_interface_decl->ivar_begin(); ivar_pos != ivar_end; ++ivar_pos)
- {
- if (child_idx == idx)
- {
- clang::ObjCIvarDecl* ivar_decl = *ivar_pos;
-
- clang::QualType ivar_qual_type(ivar_decl->getType());
-
- child_name.assign(ivar_decl->getNameAsString().c_str());
-
- clang::TypeInfo ivar_type_info = getASTContext()->getTypeInfo(ivar_qual_type.getTypePtr());
-
- child_byte_size = ivar_type_info.Width / 8;
-
- // Figure out the field offset within the current struct/union/class type
- // For ObjC objects, we can't trust the bit offset we get from the Clang AST, since
- // that doesn't account for the space taken up by unbacked properties, or from
- // the changing size of base classes that are newer than this class.
- // So if we have a process around that we can ask about this object, do so.
- child_byte_offset = LLDB_INVALID_IVAR_OFFSET;
- Process *process = nullptr;
- if (exe_ctx)
- process = exe_ctx->GetProcessPtr();
- if (process)
- {
- ObjCLanguageRuntime *objc_runtime = process->GetObjCLanguageRuntime();
- if (objc_runtime != nullptr)
- {
- CompilerType parent_ast_type (getASTContext(), parent_qual_type);
- child_byte_offset = objc_runtime->GetByteOffsetForIvar (parent_ast_type, ivar_decl->getNameAsString().c_str());
- }
- }
-
- // Setting this to UINT32_MAX to make sure we don't compute it twice...
- bit_offset = UINT32_MAX;
-
- if (child_byte_offset == static_cast<int32_t>(LLDB_INVALID_IVAR_OFFSET))
- {
- bit_offset = interface_layout.getFieldOffset (child_idx - superclass_idx);
- child_byte_offset = bit_offset / 8;
- }
-
- // Note, the ObjC Ivar Byte offset is just that, it doesn't account for the bit offset
- // of a bitfield within its containing object. So regardless of where we get the byte
- // offset from, we still need to get the bit offset for bitfields from the layout.
-
- if (ClangASTContext::FieldIsBitfield (getASTContext(), ivar_decl, child_bitfield_bit_size))
- {
- if (bit_offset == UINT32_MAX)
- bit_offset = interface_layout.getFieldOffset (child_idx - superclass_idx);
-
- child_bitfield_bit_offset = bit_offset % 8;
- }
- return CompilerType (getASTContext(), ivar_qual_type);
- }
- ++child_idx;
+ } else {
+ clang::ItaniumVTableContext *itanium_vtable_ctx =
+ static_cast<clang::ItaniumVTableContext *>(
+ vtable_ctx);
+ if (vtable_ptr_addr) {
+ const lldb::addr_t vtable_ptr =
+ process->ReadPointerFromMemory(vtable_ptr_addr,
+ err);
+ if (vtable_ptr != LLDB_INVALID_ADDRESS) {
+ clang::CharUnits base_offset_offset =
+ itanium_vtable_ctx->getVirtualBaseOffsetOffset(
+ cxx_record_decl, base_class_decl);
+ const lldb::addr_t base_offset_addr =
+ vtable_ptr + base_offset_offset.getQuantity();
+ const uint32_t base_offset_size =
+ process->GetAddressByteSize();
+ const uint64_t base_offset =
+ process->ReadUnsignedIntegerFromMemory(
+ base_offset_addr, base_offset_size,
+ UINT32_MAX, err);
+ if (base_offset < UINT32_MAX) {
+ handled = true;
+ bit_offset = base_offset * 8;
}
+ }
}
+ }
}
+ }
}
- }
- break;
-
- case clang::Type::ObjCObjectPointer:
- if (idx_is_valid)
- {
- CompilerType pointee_clang_type (GetPointeeType(type));
-
- if (transparent_pointers && pointee_clang_type.IsAggregateType())
- {
- child_is_deref_of_parent = false;
- bool tmp_child_is_deref_of_parent = false;
- return pointee_clang_type.GetChildCompilerTypeAtIndex (exe_ctx,
- idx,
- transparent_pointers,
- omit_empty_base_classes,
- ignore_array_bounds,
- child_name,
- child_byte_size,
- child_byte_offset,
- child_bitfield_bit_size,
- child_bitfield_bit_offset,
- child_is_base_class,
- tmp_child_is_deref_of_parent,
- valobj,
- language_flags);
- }
- else
- {
- child_is_deref_of_parent = true;
- const char *parent_name = valobj ? valobj->GetName().GetCString() : NULL;
- if (parent_name)
- {
- child_name.assign(1, '*');
- child_name += parent_name;
- }
-
- // We have a pointer to an simple type
- if (idx == 0 && pointee_clang_type.GetCompleteType())
- {
- child_byte_size = pointee_clang_type.GetByteSize(exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
- child_byte_offset = 0;
- return pointee_clang_type;
- }
- }
- }
- break;
-
- case clang::Type::Vector:
- case clang::Type::ExtVector:
- if (idx_is_valid)
- {
- const clang::VectorType *array = llvm::cast<clang::VectorType>(parent_qual_type.getTypePtr());
- if (array)
- {
- CompilerType element_type (getASTContext(), array->getElementType());
- if (element_type.GetCompleteType())
- {
- char element_name[64];
- ::snprintf (element_name, sizeof (element_name), "[%" PRIu64 "]", static_cast<uint64_t>(idx));
- child_name.assign(element_name);
- child_byte_size = element_type.GetByteSize(exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
- child_byte_offset = (int32_t)idx * (int32_t)child_byte_size;
- return element_type;
- }
- }
- }
- break;
-
- case clang::Type::ConstantArray:
- case clang::Type::IncompleteArray:
- if (ignore_array_bounds || idx_is_valid)
- {
- const clang::ArrayType *array = GetQualType(type)->getAsArrayTypeUnsafe();
- if (array)
- {
- CompilerType element_type (getASTContext(), array->getElementType());
- if (element_type.GetCompleteType())
- {
- char element_name[64];
- ::snprintf (element_name, sizeof (element_name), "[%" PRIu64 "]", static_cast<uint64_t>(idx));
- child_name.assign(element_name);
- child_byte_size = element_type.GetByteSize(exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
- child_byte_offset = (int32_t)idx * (int32_t)child_byte_size;
- return element_type;
- }
- }
- }
- break;
-
-
- case clang::Type::Pointer:
- if (idx_is_valid)
- {
- CompilerType pointee_clang_type (GetPointeeType(type));
-
- // Don't dereference "void *" pointers
- if (pointee_clang_type.IsVoidType())
- return CompilerType();
-
- if (transparent_pointers && pointee_clang_type.IsAggregateType ())
- {
- child_is_deref_of_parent = false;
- bool tmp_child_is_deref_of_parent = false;
- return pointee_clang_type.GetChildCompilerTypeAtIndex (exe_ctx,
- idx,
- transparent_pointers,
- omit_empty_base_classes,
- ignore_array_bounds,
- child_name,
- child_byte_size,
- child_byte_offset,
- child_bitfield_bit_size,
- child_bitfield_bit_offset,
- child_is_base_class,
- tmp_child_is_deref_of_parent,
- valobj,
- language_flags);
+ }
+ if (!handled)
+ bit_offset = record_layout.getVBaseClassOffset(base_class_decl)
+ .getQuantity() *
+ 8;
+ } else
+ bit_offset = record_layout.getBaseClassOffset(base_class_decl)
+ .getQuantity() *
+ 8;
+
+ // Base classes should be a multiple of 8 bits in size
+ child_byte_offset = bit_offset / 8;
+ CompilerType base_class_clang_type(getASTContext(),
+ base_class->getType());
+ child_name = base_class_clang_type.GetTypeName().AsCString("");
+ uint64_t base_class_clang_type_bit_size =
+ base_class_clang_type.GetBitSize(
+ exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
+
+ // Base classes bit sizes should be a multiple of 8 bits in size
+ assert(base_class_clang_type_bit_size % 8 == 0);
+ child_byte_size = base_class_clang_type_bit_size / 8;
+ child_is_base_class = true;
+ return base_class_clang_type;
+ }
+ // We don't increment the child index in the for loop since we might
+ // be skipping empty base classes
+ ++child_idx;
+ }
+ }
+ // Make sure index is in range...
+ uint32_t field_idx = 0;
+ clang::RecordDecl::field_iterator field, field_end;
+ for (field = record_decl->field_begin(),
+ field_end = record_decl->field_end();
+ field != field_end; ++field, ++field_idx, ++child_idx) {
+ if (idx == child_idx) {
+ // Print the member type if requested
+ // Print the member name and equal sign
+ child_name.assign(field->getNameAsString().c_str());
+
+ // Figure out the type byte size (field_type_info.first) and
+ // alignment (field_type_info.second) from the AST context.
+ CompilerType field_clang_type(getASTContext(), field->getType());
+ assert(field_idx < record_layout.getFieldCount());
+ child_byte_size = field_clang_type.GetByteSize(
+ exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
+ const uint32_t child_bit_size = child_byte_size * 8;
+
+ // Figure out the field offset within the current struct/union/class
+ // type
+ bit_offset = record_layout.getFieldOffset(field_idx);
+ if (ClangASTContext::FieldIsBitfield(getASTContext(), *field,
+ child_bitfield_bit_size)) {
+ child_bitfield_bit_offset = bit_offset % child_bit_size;
+ const uint32_t child_bit_offset =
+ bit_offset - child_bitfield_bit_offset;
+ child_byte_offset = child_bit_offset / 8;
+ } else {
+ child_byte_offset = bit_offset / 8;
+ }
+
+ return field_clang_type;
+ }
+ }
+ }
+ break;
+
+ case clang::Type::ObjCObject:
+ case clang::Type::ObjCInterface:
+ if (idx_is_valid && GetCompleteType(type)) {
+ const clang::ObjCObjectType *objc_class_type =
+ llvm::dyn_cast<clang::ObjCObjectType>(parent_qual_type.getTypePtr());
+ assert(objc_class_type);
+ if (objc_class_type) {
+ uint32_t child_idx = 0;
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterface();
+
+ if (class_interface_decl) {
+
+ const clang::ASTRecordLayout &interface_layout =
+ getASTContext()->getASTObjCInterfaceLayout(class_interface_decl);
+ clang::ObjCInterfaceDecl *superclass_interface_decl =
+ class_interface_decl->getSuperClass();
+ if (superclass_interface_decl) {
+ if (omit_empty_base_classes) {
+ CompilerType base_class_clang_type(
+ getASTContext(), getASTContext()->getObjCInterfaceType(
+ superclass_interface_decl));
+ if (base_class_clang_type.GetNumChildren(
+ omit_empty_base_classes) > 0) {
+ if (idx == 0) {
+ clang::QualType ivar_qual_type(
+ getASTContext()->getObjCInterfaceType(
+ superclass_interface_decl));
+
+ child_name.assign(
+ superclass_interface_decl->getNameAsString().c_str());
+
+ clang::TypeInfo ivar_type_info =
+ getASTContext()->getTypeInfo(ivar_qual_type.getTypePtr());
+
+ child_byte_size = ivar_type_info.Width / 8;
+ child_byte_offset = 0;
+ child_is_base_class = true;
+
+ return CompilerType(getASTContext(), ivar_qual_type);
}
- else
- {
- child_is_deref_of_parent = true;
-
- const char *parent_name = valobj ? valobj->GetName().GetCString() : NULL;
- if (parent_name)
- {
- child_name.assign(1, '*');
- child_name += parent_name;
- }
-
- // We have a pointer to an simple type
- if (idx == 0)
- {
- child_byte_size = pointee_clang_type.GetByteSize(exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
- child_byte_offset = 0;
- return pointee_clang_type;
- }
+
+ ++child_idx;
+ }
+ } else
+ ++child_idx;
+ }
+
+ const uint32_t superclass_idx = child_idx;
+
+ if (idx < (child_idx + class_interface_decl->ivar_size())) {
+ clang::ObjCInterfaceDecl::ivar_iterator ivar_pos,
+ ivar_end = class_interface_decl->ivar_end();
+
+ for (ivar_pos = class_interface_decl->ivar_begin();
+ ivar_pos != ivar_end; ++ivar_pos) {
+ if (child_idx == idx) {
+ clang::ObjCIvarDecl *ivar_decl = *ivar_pos;
+
+ clang::QualType ivar_qual_type(ivar_decl->getType());
+
+ child_name.assign(ivar_decl->getNameAsString().c_str());
+
+ clang::TypeInfo ivar_type_info =
+ getASTContext()->getTypeInfo(ivar_qual_type.getTypePtr());
+
+ child_byte_size = ivar_type_info.Width / 8;
+
+ // Figure out the field offset within the current
+ // struct/union/class type
+ // For ObjC objects, we can't trust the bit offset we get from
+ // the Clang AST, since
+ // that doesn't account for the space taken up by unbacked
+ // properties, or from
+ // the changing size of base classes that are newer than this
+ // class.
+ // So if we have a process around that we can ask about this
+ // object, do so.
+ child_byte_offset = LLDB_INVALID_IVAR_OFFSET;
+ Process *process = nullptr;
+ if (exe_ctx)
+ process = exe_ctx->GetProcessPtr();
+ if (process) {
+ ObjCLanguageRuntime *objc_runtime =
+ process->GetObjCLanguageRuntime();
+ if (objc_runtime != nullptr) {
+ CompilerType parent_ast_type(getASTContext(),
+ parent_qual_type);
+ child_byte_offset = objc_runtime->GetByteOffsetForIvar(
+ parent_ast_type, ivar_decl->getNameAsString().c_str());
+ }
}
- }
- break;
-
- case clang::Type::LValueReference:
- case clang::Type::RValueReference:
- if (idx_is_valid)
- {
- const clang::ReferenceType *reference_type = llvm::cast<clang::ReferenceType>(parent_qual_type.getTypePtr());
- CompilerType pointee_clang_type (getASTContext(), reference_type->getPointeeType());
- if (transparent_pointers && pointee_clang_type.IsAggregateType ())
- {
- child_is_deref_of_parent = false;
- bool tmp_child_is_deref_of_parent = false;
- return pointee_clang_type.GetChildCompilerTypeAtIndex (exe_ctx,
- idx,
- transparent_pointers,
- omit_empty_base_classes,
- ignore_array_bounds,
- child_name,
- child_byte_size,
- child_byte_offset,
- child_bitfield_bit_size,
- child_bitfield_bit_offset,
- child_is_base_class,
- tmp_child_is_deref_of_parent,
- valobj,
- language_flags);
+
+ // Setting this to UINT32_MAX to make sure we don't compute it
+ // twice...
+ bit_offset = UINT32_MAX;
+
+ if (child_byte_offset ==
+ static_cast<int32_t>(LLDB_INVALID_IVAR_OFFSET)) {
+ bit_offset = interface_layout.getFieldOffset(child_idx -
+ superclass_idx);
+ child_byte_offset = bit_offset / 8;
}
- else
- {
- const char *parent_name = valobj ? valobj->GetName().GetCString() : NULL;
- if (parent_name)
- {
- child_name.assign(1, '&');
- child_name += parent_name;
- }
-
- // We have a pointer to an simple type
- if (idx == 0)
- {
- child_byte_size = pointee_clang_type.GetByteSize(exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
- child_byte_offset = 0;
- return pointee_clang_type;
- }
+
+ // Note, the ObjC Ivar Byte offset is just that, it doesn't
+ // account for the bit offset
+ // of a bitfield within its containing object. So regardless of
+ // where we get the byte
+ // offset from, we still need to get the bit offset for
+ // bitfields from the layout.
+
+ if (ClangASTContext::FieldIsBitfield(getASTContext(), ivar_decl,
+ child_bitfield_bit_size)) {
+ if (bit_offset == UINT32_MAX)
+ bit_offset = interface_layout.getFieldOffset(
+ child_idx - superclass_idx);
+
+ child_bitfield_bit_offset = bit_offset % 8;
}
+ return CompilerType(getASTContext(), ivar_qual_type);
+ }
+ ++child_idx;
}
- break;
-
- case clang::Type::Typedef:
- {
- CompilerType typedefed_clang_type (getASTContext(), llvm::cast<clang::TypedefType>(parent_qual_type)->getDecl()->getUnderlyingType());
- return typedefed_clang_type.GetChildCompilerTypeAtIndex (exe_ctx,
- idx,
- transparent_pointers,
- omit_empty_base_classes,
- ignore_array_bounds,
- child_name,
- child_byte_size,
- child_byte_offset,
- child_bitfield_bit_size,
- child_bitfield_bit_offset,
- child_is_base_class,
- child_is_deref_of_parent,
- valobj,
- language_flags);
+ }
}
- break;
-
- case clang::Type::Auto:
- {
- CompilerType elaborated_clang_type (getASTContext(), llvm::cast<clang::AutoType>(parent_qual_type)->getDeducedType());
- return elaborated_clang_type.GetChildCompilerTypeAtIndex (exe_ctx,
- idx,
- transparent_pointers,
- omit_empty_base_classes,
- ignore_array_bounds,
- child_name,
- child_byte_size,
- child_byte_offset,
- child_bitfield_bit_size,
- child_bitfield_bit_offset,
- child_is_base_class,
- child_is_deref_of_parent,
- valobj,
- language_flags);
+ }
+ }
+ break;
+
+ case clang::Type::ObjCObjectPointer:
+ if (idx_is_valid) {
+ CompilerType pointee_clang_type(GetPointeeType(type));
+
+ if (transparent_pointers && pointee_clang_type.IsAggregateType()) {
+ child_is_deref_of_parent = false;
+ bool tmp_child_is_deref_of_parent = false;
+ return pointee_clang_type.GetChildCompilerTypeAtIndex(
+ exe_ctx, idx, transparent_pointers, omit_empty_base_classes,
+ ignore_array_bounds, child_name, child_byte_size, child_byte_offset,
+ child_bitfield_bit_size, child_bitfield_bit_offset,
+ child_is_base_class, tmp_child_is_deref_of_parent, valobj,
+ language_flags);
+ } else {
+ child_is_deref_of_parent = true;
+ const char *parent_name =
+ valobj ? valobj->GetName().GetCString() : NULL;
+ if (parent_name) {
+ child_name.assign(1, '*');
+ child_name += parent_name;
}
-
- case clang::Type::Elaborated:
- {
- CompilerType elaborated_clang_type (getASTContext(), llvm::cast<clang::ElaboratedType>(parent_qual_type)->getNamedType());
- return elaborated_clang_type.GetChildCompilerTypeAtIndex (exe_ctx,
- idx,
- transparent_pointers,
- omit_empty_base_classes,
- ignore_array_bounds,
- child_name,
- child_byte_size,
- child_byte_offset,
- child_bitfield_bit_size,
- child_bitfield_bit_offset,
- child_is_base_class,
- child_is_deref_of_parent,
- valobj,
- language_flags);
+
+ // We have a pointer to an simple type
+ if (idx == 0 && pointee_clang_type.GetCompleteType()) {
+ child_byte_size = pointee_clang_type.GetByteSize(
+ exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
+ child_byte_offset = 0;
+ return pointee_clang_type;
}
-
- case clang::Type::Paren:
- {
- CompilerType paren_clang_type (getASTContext(), llvm::cast<clang::ParenType>(parent_qual_type)->desugar());
- return paren_clang_type.GetChildCompilerTypeAtIndex (exe_ctx,
- idx,
- transparent_pointers,
- omit_empty_base_classes,
- ignore_array_bounds,
- child_name,
- child_byte_size,
- child_byte_offset,
- child_bitfield_bit_size,
- child_bitfield_bit_offset,
- child_is_base_class,
- child_is_deref_of_parent,
- valobj,
- language_flags);
+ }
+ }
+ break;
+
+ case clang::Type::Vector:
+ case clang::Type::ExtVector:
+ if (idx_is_valid) {
+ const clang::VectorType *array =
+ llvm::cast<clang::VectorType>(parent_qual_type.getTypePtr());
+ if (array) {
+ CompilerType element_type(getASTContext(), array->getElementType());
+ if (element_type.GetCompleteType()) {
+ char element_name[64];
+ ::snprintf(element_name, sizeof(element_name), "[%" PRIu64 "]",
+ static_cast<uint64_t>(idx));
+ child_name.assign(element_name);
+ child_byte_size = element_type.GetByteSize(
+ exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
+ child_byte_offset = (int32_t)idx * (int32_t)child_byte_size;
+ return element_type;
}
-
-
- default:
- break;
+ }
+ }
+ break;
+
+ case clang::Type::ConstantArray:
+ case clang::Type::IncompleteArray:
+ if (ignore_array_bounds || idx_is_valid) {
+ const clang::ArrayType *array = GetQualType(type)->getAsArrayTypeUnsafe();
+ if (array) {
+ CompilerType element_type(getASTContext(), array->getElementType());
+ if (element_type.GetCompleteType()) {
+ char element_name[64];
+ ::snprintf(element_name, sizeof(element_name), "[%" PRIu64 "]",
+ static_cast<uint64_t>(idx));
+ child_name.assign(element_name);
+ child_byte_size = element_type.GetByteSize(
+ exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
+ child_byte_offset = (int32_t)idx * (int32_t)child_byte_size;
+ return element_type;
+ }
+ }
}
- return CompilerType();
-}
+ break;
-static uint32_t
-GetIndexForRecordBase
-(
- const clang::RecordDecl *record_decl,
- const clang::CXXBaseSpecifier *base_spec,
- bool omit_empty_base_classes
- )
-{
- uint32_t child_idx = 0;
-
- const clang::CXXRecordDecl *cxx_record_decl = llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
-
- // const char *super_name = record_decl->getNameAsCString();
- // const char *base_name = base_spec->getType()->getAs<clang::RecordType>()->getDecl()->getNameAsCString();
- // printf ("GetIndexForRecordChild (%s, %s)\n", super_name, base_name);
- //
- if (cxx_record_decl)
- {
- clang::CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
- for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end();
- base_class != base_class_end;
- ++base_class)
- {
- if (omit_empty_base_classes)
- {
- if (BaseSpecifierIsEmpty (base_class))
- continue;
- }
-
- // printf ("GetIndexForRecordChild (%s, %s) base[%u] = %s\n", super_name, base_name,
- // child_idx,
- // base_class->getType()->getAs<clang::RecordType>()->getDecl()->getNameAsCString());
- //
- //
- if (base_class == base_spec)
- return child_idx;
- ++child_idx;
+ case clang::Type::Pointer:
+ if (idx_is_valid) {
+ CompilerType pointee_clang_type(GetPointeeType(type));
+
+ // Don't dereference "void *" pointers
+ if (pointee_clang_type.IsVoidType())
+ return CompilerType();
+
+ if (transparent_pointers && pointee_clang_type.IsAggregateType()) {
+ child_is_deref_of_parent = false;
+ bool tmp_child_is_deref_of_parent = false;
+ return pointee_clang_type.GetChildCompilerTypeAtIndex(
+ exe_ctx, idx, transparent_pointers, omit_empty_base_classes,
+ ignore_array_bounds, child_name, child_byte_size, child_byte_offset,
+ child_bitfield_bit_size, child_bitfield_bit_offset,
+ child_is_base_class, tmp_child_is_deref_of_parent, valobj,
+ language_flags);
+ } else {
+ child_is_deref_of_parent = true;
+
+ const char *parent_name =
+ valobj ? valobj->GetName().GetCString() : NULL;
+ if (parent_name) {
+ child_name.assign(1, '*');
+ child_name += parent_name;
}
- }
-
- return UINT32_MAX;
-}
+ // We have a pointer to an simple type
+ if (idx == 0) {
+ child_byte_size = pointee_clang_type.GetByteSize(
+ exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
+ child_byte_offset = 0;
+ return pointee_clang_type;
+ }
+ }
+ }
+ break;
+
+ case clang::Type::LValueReference:
+ case clang::Type::RValueReference:
+ if (idx_is_valid) {
+ const clang::ReferenceType *reference_type =
+ llvm::cast<clang::ReferenceType>(parent_qual_type.getTypePtr());
+ CompilerType pointee_clang_type(getASTContext(),
+ reference_type->getPointeeType());
+ if (transparent_pointers && pointee_clang_type.IsAggregateType()) {
+ child_is_deref_of_parent = false;
+ bool tmp_child_is_deref_of_parent = false;
+ return pointee_clang_type.GetChildCompilerTypeAtIndex(
+ exe_ctx, idx, transparent_pointers, omit_empty_base_classes,
+ ignore_array_bounds, child_name, child_byte_size, child_byte_offset,
+ child_bitfield_bit_size, child_bitfield_bit_offset,
+ child_is_base_class, tmp_child_is_deref_of_parent, valobj,
+ language_flags);
+ } else {
+ const char *parent_name =
+ valobj ? valobj->GetName().GetCString() : NULL;
+ if (parent_name) {
+ child_name.assign(1, '&');
+ child_name += parent_name;
+ }
-static uint32_t
-GetIndexForRecordChild (const clang::RecordDecl *record_decl,
- clang::NamedDecl *canonical_decl,
- bool omit_empty_base_classes)
-{
- uint32_t child_idx = ClangASTContext::GetNumBaseClasses (llvm::dyn_cast<clang::CXXRecordDecl>(record_decl),
- omit_empty_base_classes);
-
- clang::RecordDecl::field_iterator field, field_end;
- for (field = record_decl->field_begin(), field_end = record_decl->field_end();
- field != field_end;
- ++field, ++child_idx)
- {
- if (field->getCanonicalDecl() == canonical_decl)
- return child_idx;
- }
-
- return UINT32_MAX;
+ // We have a pointer to an simple type
+ if (idx == 0) {
+ child_byte_size = pointee_clang_type.GetByteSize(
+ exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
+ child_byte_offset = 0;
+ return pointee_clang_type;
+ }
+ }
+ }
+ break;
+
+ case clang::Type::Typedef: {
+ CompilerType typedefed_clang_type(
+ getASTContext(), llvm::cast<clang::TypedefType>(parent_qual_type)
+ ->getDecl()
+ ->getUnderlyingType());
+ return typedefed_clang_type.GetChildCompilerTypeAtIndex(
+ exe_ctx, idx, transparent_pointers, omit_empty_base_classes,
+ ignore_array_bounds, child_name, child_byte_size, child_byte_offset,
+ child_bitfield_bit_size, child_bitfield_bit_offset, child_is_base_class,
+ child_is_deref_of_parent, valobj, language_flags);
+ } break;
+
+ case clang::Type::Auto: {
+ CompilerType elaborated_clang_type(
+ getASTContext(),
+ llvm::cast<clang::AutoType>(parent_qual_type)->getDeducedType());
+ return elaborated_clang_type.GetChildCompilerTypeAtIndex(
+ exe_ctx, idx, transparent_pointers, omit_empty_base_classes,
+ ignore_array_bounds, child_name, child_byte_size, child_byte_offset,
+ child_bitfield_bit_size, child_bitfield_bit_offset, child_is_base_class,
+ child_is_deref_of_parent, valobj, language_flags);
+ }
+
+ case clang::Type::Elaborated: {
+ CompilerType elaborated_clang_type(
+ getASTContext(),
+ llvm::cast<clang::ElaboratedType>(parent_qual_type)->getNamedType());
+ return elaborated_clang_type.GetChildCompilerTypeAtIndex(
+ exe_ctx, idx, transparent_pointers, omit_empty_base_classes,
+ ignore_array_bounds, child_name, child_byte_size, child_byte_offset,
+ child_bitfield_bit_size, child_bitfield_bit_offset, child_is_base_class,
+ child_is_deref_of_parent, valobj, language_flags);
+ }
+
+ case clang::Type::Paren: {
+ CompilerType paren_clang_type(
+ getASTContext(),
+ llvm::cast<clang::ParenType>(parent_qual_type)->desugar());
+ return paren_clang_type.GetChildCompilerTypeAtIndex(
+ exe_ctx, idx, transparent_pointers, omit_empty_base_classes,
+ ignore_array_bounds, child_name, child_byte_size, child_byte_offset,
+ child_bitfield_bit_size, child_bitfield_bit_offset, child_is_base_class,
+ child_is_deref_of_parent, valobj, language_flags);
+ }
+
+ default:
+ break;
+ }
+ return CompilerType();
+}
+
+static uint32_t GetIndexForRecordBase(const clang::RecordDecl *record_decl,
+ const clang::CXXBaseSpecifier *base_spec,
+ bool omit_empty_base_classes) {
+ uint32_t child_idx = 0;
+
+ const clang::CXXRecordDecl *cxx_record_decl =
+ llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
+
+ // const char *super_name = record_decl->getNameAsCString();
+ // const char *base_name =
+ // base_spec->getType()->getAs<clang::RecordType>()->getDecl()->getNameAsCString();
+ // printf ("GetIndexForRecordChild (%s, %s)\n", super_name, base_name);
+ //
+ if (cxx_record_decl) {
+ clang::CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
+ for (base_class = cxx_record_decl->bases_begin(),
+ base_class_end = cxx_record_decl->bases_end();
+ base_class != base_class_end; ++base_class) {
+ if (omit_empty_base_classes) {
+ if (BaseSpecifierIsEmpty(base_class))
+ continue;
+ }
+
+ // printf ("GetIndexForRecordChild (%s, %s) base[%u] = %s\n",
+ // super_name, base_name,
+ // child_idx,
+ // base_class->getType()->getAs<clang::RecordType>()->getDecl()->getNameAsCString());
+ //
+ //
+ if (base_class == base_spec)
+ return child_idx;
+ ++child_idx;
+ }
+ }
+
+ return UINT32_MAX;
+}
+
+static uint32_t GetIndexForRecordChild(const clang::RecordDecl *record_decl,
+ clang::NamedDecl *canonical_decl,
+ bool omit_empty_base_classes) {
+ uint32_t child_idx = ClangASTContext::GetNumBaseClasses(
+ llvm::dyn_cast<clang::CXXRecordDecl>(record_decl),
+ omit_empty_base_classes);
+
+ clang::RecordDecl::field_iterator field, field_end;
+ for (field = record_decl->field_begin(), field_end = record_decl->field_end();
+ field != field_end; ++field, ++child_idx) {
+ if (field->getCanonicalDecl() == canonical_decl)
+ return child_idx;
+ }
+
+ return UINT32_MAX;
}
// Look for a child member (doesn't include base classes, but it does include
@@ -7046,2859 +6933,2849 @@ GetIndexForRecordChild (const clang::RecordDecl *record_decl,
// If we have a clang type that describes "class C", and we wanted to looked
// "m_b" in it:
//
-// With omit_empty_base_classes == false we would get an integer array back with:
+// With omit_empty_base_classes == false we would get an integer array back
+// with:
// { 1, 1 }
// The first index 1 is the child index for "class A" within class C
// The second index 1 is the child index for "m_b" within class A
//
// With omit_empty_base_classes == true we would get an integer array back with:
// { 0, 1 }
-// The first index 0 is the child index for "class A" within class C (since class B doesn't have any members it doesn't count)
+// The first index 0 is the child index for "class A" within class C (since
+// class B doesn't have any members it doesn't count)
// The second index 1 is the child index for "m_b" within class A
-size_t
-ClangASTContext::GetIndexOfChildMemberWithName (lldb::opaque_compiler_type_t type, const char *name,
- bool omit_empty_base_classes,
- std::vector<uint32_t>& child_indexes)
-{
- if (type && name && name[0])
- {
- clang::QualType qual_type(GetCanonicalQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Record:
- if (GetCompleteType(type))
- {
- const clang::RecordType *record_type = llvm::cast<clang::RecordType>(qual_type.getTypePtr());
- const clang::RecordDecl *record_decl = record_type->getDecl();
-
- assert(record_decl);
- uint32_t child_idx = 0;
-
- const clang::CXXRecordDecl *cxx_record_decl = llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
-
- // Try and find a field that matches NAME
- clang::RecordDecl::field_iterator field, field_end;
- llvm::StringRef name_sref(name);
- for (field = record_decl->field_begin(), field_end = record_decl->field_end();
- field != field_end;
- ++field, ++child_idx)
- {
- llvm::StringRef field_name = field->getName();
- if (field_name.empty())
- {
- CompilerType field_type(getASTContext(),field->getType());
- child_indexes.push_back(child_idx);
- if (field_type.GetIndexOfChildMemberWithName(name, omit_empty_base_classes, child_indexes))
- return child_indexes.size();
- child_indexes.pop_back();
-
- }
- else if (field_name.equals (name_sref))
- {
- // We have to add on the number of base classes to this index!
- child_indexes.push_back (child_idx + ClangASTContext::GetNumBaseClasses (cxx_record_decl, omit_empty_base_classes));
- return child_indexes.size();
- }
- }
-
- if (cxx_record_decl)
- {
- const clang::RecordDecl *parent_record_decl = cxx_record_decl;
-
- //printf ("parent = %s\n", parent_record_decl->getNameAsCString());
-
- //const Decl *root_cdecl = cxx_record_decl->getCanonicalDecl();
- // Didn't find things easily, lets let clang do its thang...
- clang::IdentifierInfo & ident_ref = getASTContext()->Idents.get(name_sref);
- clang::DeclarationName decl_name(&ident_ref);
-
- clang::CXXBasePaths paths;
- if (cxx_record_decl->lookupInBases([decl_name](const clang::CXXBaseSpecifier *specifier, clang::CXXBasePath &path) {
- return clang::CXXRecordDecl::FindOrdinaryMember(specifier, path, decl_name);
- },
- paths))
- {
- clang::CXXBasePaths::const_paths_iterator path, path_end = paths.end();
- for (path = paths.begin(); path != path_end; ++path)
- {
- const size_t num_path_elements = path->size();
- for (size_t e=0; e<num_path_elements; ++e)
- {
- clang::CXXBasePathElement elem = (*path)[e];
-
- child_idx = GetIndexForRecordBase (parent_record_decl, elem.Base, omit_empty_base_classes);
- if (child_idx == UINT32_MAX)
- {
- child_indexes.clear();
- return 0;
- }
- else
- {
- child_indexes.push_back (child_idx);
- parent_record_decl = llvm::cast<clang::RecordDecl>(elem.Base->getType()->getAs<clang::RecordType>()->getDecl());
- }
- }
- for (clang::NamedDecl *path_decl : path->Decls)
- {
- child_idx = GetIndexForRecordChild (parent_record_decl, path_decl, omit_empty_base_classes);
- if (child_idx == UINT32_MAX)
- {
- child_indexes.clear();
- return 0;
- }
- else
- {
- child_indexes.push_back (child_idx);
- }
- }
- }
- return child_indexes.size();
- }
- }
-
+size_t ClangASTContext::GetIndexOfChildMemberWithName(
+ lldb::opaque_compiler_type_t type, const char *name,
+ bool omit_empty_base_classes, std::vector<uint32_t> &child_indexes) {
+ if (type && name && name[0]) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Record:
+ if (GetCompleteType(type)) {
+ const clang::RecordType *record_type =
+ llvm::cast<clang::RecordType>(qual_type.getTypePtr());
+ const clang::RecordDecl *record_decl = record_type->getDecl();
+
+ assert(record_decl);
+ uint32_t child_idx = 0;
+
+ const clang::CXXRecordDecl *cxx_record_decl =
+ llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
+
+ // Try and find a field that matches NAME
+ clang::RecordDecl::field_iterator field, field_end;
+ llvm::StringRef name_sref(name);
+ for (field = record_decl->field_begin(),
+ field_end = record_decl->field_end();
+ field != field_end; ++field, ++child_idx) {
+ llvm::StringRef field_name = field->getName();
+ if (field_name.empty()) {
+ CompilerType field_type(getASTContext(), field->getType());
+ child_indexes.push_back(child_idx);
+ if (field_type.GetIndexOfChildMemberWithName(
+ name, omit_empty_base_classes, child_indexes))
+ return child_indexes.size();
+ child_indexes.pop_back();
+
+ } else if (field_name.equals(name_sref)) {
+ // We have to add on the number of base classes to this index!
+ child_indexes.push_back(
+ child_idx + ClangASTContext::GetNumBaseClasses(
+ cxx_record_decl, omit_empty_base_classes));
+ return child_indexes.size();
+ }
+ }
+
+ if (cxx_record_decl) {
+ const clang::RecordDecl *parent_record_decl = cxx_record_decl;
+
+ // printf ("parent = %s\n", parent_record_decl->getNameAsCString());
+
+ // const Decl *root_cdecl = cxx_record_decl->getCanonicalDecl();
+ // Didn't find things easily, lets let clang do its thang...
+ clang::IdentifierInfo &ident_ref =
+ getASTContext()->Idents.get(name_sref);
+ clang::DeclarationName decl_name(&ident_ref);
+
+ clang::CXXBasePaths paths;
+ if (cxx_record_decl->lookupInBases(
+ [decl_name](const clang::CXXBaseSpecifier *specifier,
+ clang::CXXBasePath &path) {
+ return clang::CXXRecordDecl::FindOrdinaryMember(
+ specifier, path, decl_name);
+ },
+ paths)) {
+ clang::CXXBasePaths::const_paths_iterator path,
+ path_end = paths.end();
+ for (path = paths.begin(); path != path_end; ++path) {
+ const size_t num_path_elements = path->size();
+ for (size_t e = 0; e < num_path_elements; ++e) {
+ clang::CXXBasePathElement elem = (*path)[e];
+
+ child_idx = GetIndexForRecordBase(parent_record_decl, elem.Base,
+ omit_empty_base_classes);
+ if (child_idx == UINT32_MAX) {
+ child_indexes.clear();
+ return 0;
+ } else {
+ child_indexes.push_back(child_idx);
+ parent_record_decl = llvm::cast<clang::RecordDecl>(
+ elem.Base->getType()
+ ->getAs<clang::RecordType>()
+ ->getDecl());
}
- break;
-
- case clang::Type::ObjCObject:
- case clang::Type::ObjCInterface:
- if (GetCompleteType(type))
- {
- llvm::StringRef name_sref(name);
- const clang::ObjCObjectType *objc_class_type = llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
- assert (objc_class_type);
- if (objc_class_type)
- {
- uint32_t child_idx = 0;
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
-
- if (class_interface_decl)
- {
- clang::ObjCInterfaceDecl::ivar_iterator ivar_pos, ivar_end = class_interface_decl->ivar_end();
- clang::ObjCInterfaceDecl *superclass_interface_decl = class_interface_decl->getSuperClass();
-
- for (ivar_pos = class_interface_decl->ivar_begin(); ivar_pos != ivar_end; ++ivar_pos, ++child_idx)
- {
- const clang::ObjCIvarDecl* ivar_decl = *ivar_pos;
-
- if (ivar_decl->getName().equals (name_sref))
- {
- if ((!omit_empty_base_classes && superclass_interface_decl) ||
- ( omit_empty_base_classes && ObjCDeclHasIVars (superclass_interface_decl, true)))
- ++child_idx;
-
- child_indexes.push_back (child_idx);
- return child_indexes.size();
- }
- }
-
- if (superclass_interface_decl)
- {
- // The super class index is always zero for ObjC classes,
- // so we push it onto the child indexes in case we find
- // an ivar in our superclass...
- child_indexes.push_back (0);
-
- CompilerType superclass_clang_type (getASTContext(), getASTContext()->getObjCInterfaceType(superclass_interface_decl));
- if (superclass_clang_type.GetIndexOfChildMemberWithName (name,
- omit_empty_base_classes,
- child_indexes))
- {
- // We did find an ivar in a superclass so just
- // return the results!
- return child_indexes.size();
- }
-
- // We didn't find an ivar matching "name" in our
- // superclass, pop the superclass zero index that
- // we pushed on above.
- child_indexes.pop_back();
- }
- }
- }
+ }
+ for (clang::NamedDecl *path_decl : path->Decls) {
+ child_idx = GetIndexForRecordChild(
+ parent_record_decl, path_decl, omit_empty_base_classes);
+ if (child_idx == UINT32_MAX) {
+ child_indexes.clear();
+ return 0;
+ } else {
+ child_indexes.push_back(child_idx);
}
- break;
-
- case clang::Type::ObjCObjectPointer:
- {
- CompilerType objc_object_clang_type (getASTContext(), llvm::cast<clang::ObjCObjectPointerType>(qual_type.getTypePtr())->getPointeeType());
- return objc_object_clang_type.GetIndexOfChildMemberWithName (name,
- omit_empty_base_classes,
- child_indexes);
+ }
}
- break;
-
-
- case clang::Type::ConstantArray:
- {
- // const clang::ConstantArrayType *array = llvm::cast<clang::ConstantArrayType>(parent_qual_type.getTypePtr());
- // const uint64_t element_count = array->getSize().getLimitedValue();
- //
- // if (idx < element_count)
- // {
- // std::pair<uint64_t, unsigned> field_type_info = ast->getTypeInfo(array->getElementType());
- //
- // char element_name[32];
- // ::snprintf (element_name, sizeof (element_name), "%s[%u]", parent_name ? parent_name : "", idx);
- //
- // child_name.assign(element_name);
- // assert(field_type_info.first % 8 == 0);
- // child_byte_size = field_type_info.first / 8;
- // child_byte_offset = idx * child_byte_size;
- // return array->getElementType().getAsOpaquePtr();
- // }
- }
- break;
-
- // case clang::Type::MemberPointerType:
- // {
- // MemberPointerType *mem_ptr_type = llvm::cast<MemberPointerType>(qual_type.getTypePtr());
- // clang::QualType pointee_type = mem_ptr_type->getPointeeType();
- //
- // if (ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr()))
- // {
- // return GetIndexOfChildWithName (ast,
- // mem_ptr_type->getPointeeType().getAsOpaquePtr(),
- // name);
- // }
- // }
- // break;
- //
- case clang::Type::LValueReference:
- case clang::Type::RValueReference:
- {
- const clang::ReferenceType *reference_type = llvm::cast<clang::ReferenceType>(qual_type.getTypePtr());
- clang::QualType pointee_type(reference_type->getPointeeType());
- CompilerType pointee_clang_type (getASTContext(), pointee_type);
-
- if (pointee_clang_type.IsAggregateType ())
- {
- return pointee_clang_type.GetIndexOfChildMemberWithName (name,
- omit_empty_base_classes,
- child_indexes);
- }
+ return child_indexes.size();
+ }
+ }
+ }
+ break;
+
+ case clang::Type::ObjCObject:
+ case clang::Type::ObjCInterface:
+ if (GetCompleteType(type)) {
+ llvm::StringRef name_sref(name);
+ const clang::ObjCObjectType *objc_class_type =
+ llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
+ assert(objc_class_type);
+ if (objc_class_type) {
+ uint32_t child_idx = 0;
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterface();
+
+ if (class_interface_decl) {
+ clang::ObjCInterfaceDecl::ivar_iterator ivar_pos,
+ ivar_end = class_interface_decl->ivar_end();
+ clang::ObjCInterfaceDecl *superclass_interface_decl =
+ class_interface_decl->getSuperClass();
+
+ for (ivar_pos = class_interface_decl->ivar_begin();
+ ivar_pos != ivar_end; ++ivar_pos, ++child_idx) {
+ const clang::ObjCIvarDecl *ivar_decl = *ivar_pos;
+
+ if (ivar_decl->getName().equals(name_sref)) {
+ if ((!omit_empty_base_classes && superclass_interface_decl) ||
+ (omit_empty_base_classes &&
+ ObjCDeclHasIVars(superclass_interface_decl, true)))
+ ++child_idx;
+
+ child_indexes.push_back(child_idx);
+ return child_indexes.size();
+ }
}
- break;
-
- case clang::Type::Pointer:
- {
- CompilerType pointee_clang_type (GetPointeeType(type));
-
- if (pointee_clang_type.IsAggregateType ())
- {
- return pointee_clang_type.GetIndexOfChildMemberWithName (name,
- omit_empty_base_classes,
- child_indexes);
- }
+
+ if (superclass_interface_decl) {
+ // The super class index is always zero for ObjC classes,
+ // so we push it onto the child indexes in case we find
+ // an ivar in our superclass...
+ child_indexes.push_back(0);
+
+ CompilerType superclass_clang_type(
+ getASTContext(), getASTContext()->getObjCInterfaceType(
+ superclass_interface_decl));
+ if (superclass_clang_type.GetIndexOfChildMemberWithName(
+ name, omit_empty_base_classes, child_indexes)) {
+ // We did find an ivar in a superclass so just
+ // return the results!
+ return child_indexes.size();
+ }
+
+ // We didn't find an ivar matching "name" in our
+ // superclass, pop the superclass zero index that
+ // we pushed on above.
+ child_indexes.pop_back();
}
- break;
-
- case clang::Type::Typedef:
- return CompilerType (getASTContext(), llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType()).GetIndexOfChildMemberWithName (name,
- omit_empty_base_classes,
- child_indexes);
-
- case clang::Type::Auto:
- return CompilerType (getASTContext(), llvm::cast<clang::AutoType>(qual_type)->getDeducedType()).GetIndexOfChildMemberWithName (name,
- omit_empty_base_classes,
- child_indexes);
-
- case clang::Type::Elaborated:
- return CompilerType (getASTContext(), llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType()).GetIndexOfChildMemberWithName (name,
- omit_empty_base_classes,
- child_indexes);
-
- case clang::Type::Paren:
- return CompilerType (getASTContext(), llvm::cast<clang::ParenType>(qual_type)->desugar()).GetIndexOfChildMemberWithName (name,
- omit_empty_base_classes,
- child_indexes);
-
- default:
- break;
+ }
}
+ }
+ break;
+
+ case clang::Type::ObjCObjectPointer: {
+ CompilerType objc_object_clang_type(
+ getASTContext(),
+ llvm::cast<clang::ObjCObjectPointerType>(qual_type.getTypePtr())
+ ->getPointeeType());
+ return objc_object_clang_type.GetIndexOfChildMemberWithName(
+ name, omit_empty_base_classes, child_indexes);
+ } break;
+
+ case clang::Type::ConstantArray: {
+ // const clang::ConstantArrayType *array =
+ // llvm::cast<clang::ConstantArrayType>(parent_qual_type.getTypePtr());
+ // const uint64_t element_count =
+ // array->getSize().getLimitedValue();
+ //
+ // if (idx < element_count)
+ // {
+ // std::pair<uint64_t, unsigned> field_type_info =
+ // ast->getTypeInfo(array->getElementType());
+ //
+ // char element_name[32];
+ // ::snprintf (element_name, sizeof (element_name),
+ // "%s[%u]", parent_name ? parent_name : "", idx);
+ //
+ // child_name.assign(element_name);
+ // assert(field_type_info.first % 8 == 0);
+ // child_byte_size = field_type_info.first / 8;
+ // child_byte_offset = idx * child_byte_size;
+ // return array->getElementType().getAsOpaquePtr();
+ // }
+ } break;
+
+ // case clang::Type::MemberPointerType:
+ // {
+ // MemberPointerType *mem_ptr_type =
+ // llvm::cast<MemberPointerType>(qual_type.getTypePtr());
+ // clang::QualType pointee_type =
+ // mem_ptr_type->getPointeeType();
+ //
+ // if (ClangASTContext::IsAggregateType
+ // (pointee_type.getAsOpaquePtr()))
+ // {
+ // return GetIndexOfChildWithName (ast,
+ // mem_ptr_type->getPointeeType().getAsOpaquePtr(),
+ // name);
+ // }
+ // }
+ // break;
+ //
+ case clang::Type::LValueReference:
+ case clang::Type::RValueReference: {
+ const clang::ReferenceType *reference_type =
+ llvm::cast<clang::ReferenceType>(qual_type.getTypePtr());
+ clang::QualType pointee_type(reference_type->getPointeeType());
+ CompilerType pointee_clang_type(getASTContext(), pointee_type);
+
+ if (pointee_clang_type.IsAggregateType()) {
+ return pointee_clang_type.GetIndexOfChildMemberWithName(
+ name, omit_empty_base_classes, child_indexes);
+ }
+ } break;
+
+ case clang::Type::Pointer: {
+ CompilerType pointee_clang_type(GetPointeeType(type));
+
+ if (pointee_clang_type.IsAggregateType()) {
+ return pointee_clang_type.GetIndexOfChildMemberWithName(
+ name, omit_empty_base_classes, child_indexes);
+ }
+ } break;
+
+ case clang::Type::Typedef:
+ return CompilerType(getASTContext(),
+ llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType())
+ .GetIndexOfChildMemberWithName(name, omit_empty_base_classes,
+ child_indexes);
+
+ case clang::Type::Auto:
+ return CompilerType(
+ getASTContext(),
+ llvm::cast<clang::AutoType>(qual_type)->getDeducedType())
+ .GetIndexOfChildMemberWithName(name, omit_empty_base_classes,
+ child_indexes);
+
+ case clang::Type::Elaborated:
+ return CompilerType(
+ getASTContext(),
+ llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType())
+ .GetIndexOfChildMemberWithName(name, omit_empty_base_classes,
+ child_indexes);
+
+ case clang::Type::Paren:
+ return CompilerType(getASTContext(),
+ llvm::cast<clang::ParenType>(qual_type)->desugar())
+ .GetIndexOfChildMemberWithName(name, omit_empty_base_classes,
+ child_indexes);
+
+ default:
+ break;
}
- return 0;
+ }
+ return 0;
}
-
// Get the index of the child of "clang_type" whose name matches. This function
// doesn't descend into the children, but only looks one level deep and name
// matches can include base class names.
uint32_t
-ClangASTContext::GetIndexOfChildWithName (lldb::opaque_compiler_type_t type, const char *name, bool omit_empty_base_classes)
-{
- if (type && name && name[0])
- {
- clang::QualType qual_type(GetCanonicalQualType(type));
-
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
-
- switch (type_class)
- {
- case clang::Type::Record:
- if (GetCompleteType(type))
- {
- const clang::RecordType *record_type = llvm::cast<clang::RecordType>(qual_type.getTypePtr());
- const clang::RecordDecl *record_decl = record_type->getDecl();
-
- assert(record_decl);
- uint32_t child_idx = 0;
-
- const clang::CXXRecordDecl *cxx_record_decl = llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
-
- if (cxx_record_decl)
- {
- clang::CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
- for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end();
- base_class != base_class_end;
- ++base_class)
- {
- // Skip empty base classes
- clang::CXXRecordDecl *base_class_decl = llvm::cast<clang::CXXRecordDecl>(base_class->getType()->getAs<clang::RecordType>()->getDecl());
- if (omit_empty_base_classes && ClangASTContext::RecordHasFields(base_class_decl) == false)
- continue;
-
- CompilerType base_class_clang_type (getASTContext(), base_class->getType());
- std::string base_class_type_name (base_class_clang_type.GetTypeName().AsCString(""));
- if (base_class_type_name.compare (name) == 0)
- return child_idx;
- ++child_idx;
- }
- }
-
- // Try and find a field that matches NAME
- clang::RecordDecl::field_iterator field, field_end;
- llvm::StringRef name_sref(name);
- for (field = record_decl->field_begin(), field_end = record_decl->field_end();
- field != field_end;
- ++field, ++child_idx)
- {
- if (field->getName().equals (name_sref))
- return child_idx;
- }
-
- }
- break;
-
- case clang::Type::ObjCObject:
- case clang::Type::ObjCInterface:
- if (GetCompleteType(type))
- {
- llvm::StringRef name_sref(name);
- const clang::ObjCObjectType *objc_class_type = llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
- assert (objc_class_type);
- if (objc_class_type)
- {
- uint32_t child_idx = 0;
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
-
- if (class_interface_decl)
- {
- clang::ObjCInterfaceDecl::ivar_iterator ivar_pos, ivar_end = class_interface_decl->ivar_end();
- clang::ObjCInterfaceDecl *superclass_interface_decl = class_interface_decl->getSuperClass();
-
- for (ivar_pos = class_interface_decl->ivar_begin(); ivar_pos != ivar_end; ++ivar_pos, ++child_idx)
- {
- const clang::ObjCIvarDecl* ivar_decl = *ivar_pos;
-
- if (ivar_decl->getName().equals (name_sref))
- {
- if ((!omit_empty_base_classes && superclass_interface_decl) ||
- ( omit_empty_base_classes && ObjCDeclHasIVars (superclass_interface_decl, true)))
- ++child_idx;
-
- return child_idx;
- }
- }
-
- if (superclass_interface_decl)
- {
- if (superclass_interface_decl->getName().equals (name_sref))
- return 0;
- }
- }
- }
- }
- break;
-
- case clang::Type::ObjCObjectPointer:
- {
- CompilerType pointee_clang_type (getASTContext(), llvm::cast<clang::ObjCObjectPointerType>(qual_type.getTypePtr())->getPointeeType());
- return pointee_clang_type.GetIndexOfChildWithName (name, omit_empty_base_classes);
- }
- break;
-
- case clang::Type::ConstantArray:
- {
- // const clang::ConstantArrayType *array = llvm::cast<clang::ConstantArrayType>(parent_qual_type.getTypePtr());
- // const uint64_t element_count = array->getSize().getLimitedValue();
- //
- // if (idx < element_count)
- // {
- // std::pair<uint64_t, unsigned> field_type_info = ast->getTypeInfo(array->getElementType());
- //
- // char element_name[32];
- // ::snprintf (element_name, sizeof (element_name), "%s[%u]", parent_name ? parent_name : "", idx);
- //
- // child_name.assign(element_name);
- // assert(field_type_info.first % 8 == 0);
- // child_byte_size = field_type_info.first / 8;
- // child_byte_offset = idx * child_byte_size;
- // return array->getElementType().getAsOpaquePtr();
- // }
- }
- break;
-
- // case clang::Type::MemberPointerType:
- // {
- // MemberPointerType *mem_ptr_type = llvm::cast<MemberPointerType>(qual_type.getTypePtr());
- // clang::QualType pointee_type = mem_ptr_type->getPointeeType();
- //
- // if (ClangASTContext::IsAggregateType (pointee_type.getAsOpaquePtr()))
- // {
- // return GetIndexOfChildWithName (ast,
- // mem_ptr_type->getPointeeType().getAsOpaquePtr(),
- // name);
- // }
- // }
- // break;
- //
- case clang::Type::LValueReference:
- case clang::Type::RValueReference:
- {
- const clang::ReferenceType *reference_type = llvm::cast<clang::ReferenceType>(qual_type.getTypePtr());
- CompilerType pointee_type (getASTContext(), reference_type->getPointeeType());
-
- if (pointee_type.IsAggregateType ())
- {
- return pointee_type.GetIndexOfChildWithName (name, omit_empty_base_classes);
- }
- }
- break;
-
- case clang::Type::Pointer:
- {
- const clang::PointerType *pointer_type = llvm::cast<clang::PointerType>(qual_type.getTypePtr());
- CompilerType pointee_type (getASTContext(), pointer_type->getPointeeType());
-
- if (pointee_type.IsAggregateType ())
- {
- return pointee_type.GetIndexOfChildWithName (name, omit_empty_base_classes);
- }
- else
- {
- // if (parent_name)
- // {
- // child_name.assign(1, '*');
- // child_name += parent_name;
- // }
- //
- // // We have a pointer to an simple type
- // if (idx == 0)
- // {
- // std::pair<uint64_t, unsigned> clang_type_info = ast->getTypeInfo(pointee_type);
- // assert(clang_type_info.first % 8 == 0);
- // child_byte_size = clang_type_info.first / 8;
- // child_byte_offset = 0;
- // return pointee_type.getAsOpaquePtr();
- // }
- }
- }
- break;
+ClangASTContext::GetIndexOfChildWithName(lldb::opaque_compiler_type_t type,
+ const char *name,
+ bool omit_empty_base_classes) {
+ if (type && name && name[0]) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
- case clang::Type::Auto:
- return CompilerType (getASTContext(), llvm::cast<clang::AutoType>(qual_type)->getDeducedType()).GetIndexOfChildWithName (name, omit_empty_base_classes);
-
- case clang::Type::Elaborated:
- return CompilerType (getASTContext(), llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType()).GetIndexOfChildWithName (name, omit_empty_base_classes);
-
- case clang::Type::Paren:
- return CompilerType (getASTContext(), llvm::cast<clang::ParenType>(qual_type)->desugar()).GetIndexOfChildWithName (name, omit_empty_base_classes);
-
- case clang::Type::Typedef:
- return CompilerType (getASTContext(), llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType()).GetIndexOfChildWithName (name, omit_empty_base_classes);
-
- default:
- break;
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+
+ switch (type_class) {
+ case clang::Type::Record:
+ if (GetCompleteType(type)) {
+ const clang::RecordType *record_type =
+ llvm::cast<clang::RecordType>(qual_type.getTypePtr());
+ const clang::RecordDecl *record_decl = record_type->getDecl();
+
+ assert(record_decl);
+ uint32_t child_idx = 0;
+
+ const clang::CXXRecordDecl *cxx_record_decl =
+ llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
+
+ if (cxx_record_decl) {
+ clang::CXXRecordDecl::base_class_const_iterator base_class,
+ base_class_end;
+ for (base_class = cxx_record_decl->bases_begin(),
+ base_class_end = cxx_record_decl->bases_end();
+ base_class != base_class_end; ++base_class) {
+ // Skip empty base classes
+ clang::CXXRecordDecl *base_class_decl =
+ llvm::cast<clang::CXXRecordDecl>(
+ base_class->getType()
+ ->getAs<clang::RecordType>()
+ ->getDecl());
+ if (omit_empty_base_classes &&
+ ClangASTContext::RecordHasFields(base_class_decl) == false)
+ continue;
+
+ CompilerType base_class_clang_type(getASTContext(),
+ base_class->getType());
+ std::string base_class_type_name(
+ base_class_clang_type.GetTypeName().AsCString(""));
+ if (base_class_type_name.compare(name) == 0)
+ return child_idx;
+ ++child_idx;
+ }
}
- }
- return UINT32_MAX;
-}
+ // Try and find a field that matches NAME
+ clang::RecordDecl::field_iterator field, field_end;
+ llvm::StringRef name_sref(name);
+ for (field = record_decl->field_begin(),
+ field_end = record_decl->field_end();
+ field != field_end; ++field, ++child_idx) {
+ if (field->getName().equals(name_sref))
+ return child_idx;
+ }
+ }
+ break;
+
+ case clang::Type::ObjCObject:
+ case clang::Type::ObjCInterface:
+ if (GetCompleteType(type)) {
+ llvm::StringRef name_sref(name);
+ const clang::ObjCObjectType *objc_class_type =
+ llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
+ assert(objc_class_type);
+ if (objc_class_type) {
+ uint32_t child_idx = 0;
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterface();
+
+ if (class_interface_decl) {
+ clang::ObjCInterfaceDecl::ivar_iterator ivar_pos,
+ ivar_end = class_interface_decl->ivar_end();
+ clang::ObjCInterfaceDecl *superclass_interface_decl =
+ class_interface_decl->getSuperClass();
+
+ for (ivar_pos = class_interface_decl->ivar_begin();
+ ivar_pos != ivar_end; ++ivar_pos, ++child_idx) {
+ const clang::ObjCIvarDecl *ivar_decl = *ivar_pos;
+
+ if (ivar_decl->getName().equals(name_sref)) {
+ if ((!omit_empty_base_classes && superclass_interface_decl) ||
+ (omit_empty_base_classes &&
+ ObjCDeclHasIVars(superclass_interface_decl, true)))
+ ++child_idx;
-size_t
-ClangASTContext::GetNumTemplateArguments (lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return 0;
+ return child_idx;
+ }
+ }
- clang::QualType qual_type (GetCanonicalQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Record:
- if (GetCompleteType(type))
- {
- const clang::CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
- if (cxx_record_decl)
- {
- const clang::ClassTemplateSpecializationDecl *template_decl = llvm::dyn_cast<clang::ClassTemplateSpecializationDecl>(cxx_record_decl);
- if (template_decl)
- return template_decl->getTemplateArgs().size();
- }
+ if (superclass_interface_decl) {
+ if (superclass_interface_decl->getName().equals(name_sref))
+ return 0;
}
- break;
-
- case clang::Type::Typedef:
- return (CompilerType (getASTContext(), llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType())).GetNumTemplateArguments();
-
- case clang::Type::Auto:
- return (CompilerType (getASTContext(), llvm::cast<clang::AutoType>(qual_type)->getDeducedType())).GetNumTemplateArguments();
-
- case clang::Type::Elaborated:
- return (CompilerType (getASTContext(), llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType())).GetNumTemplateArguments();
-
- case clang::Type::Paren:
- return (CompilerType (getASTContext(), llvm::cast<clang::ParenType>(qual_type)->desugar())).GetNumTemplateArguments();
-
- default:
- break;
- }
+ }
+ }
+ }
+ break;
+
+ case clang::Type::ObjCObjectPointer: {
+ CompilerType pointee_clang_type(
+ getASTContext(),
+ llvm::cast<clang::ObjCObjectPointerType>(qual_type.getTypePtr())
+ ->getPointeeType());
+ return pointee_clang_type.GetIndexOfChildWithName(
+ name, omit_empty_base_classes);
+ } break;
+
+ case clang::Type::ConstantArray: {
+ // const clang::ConstantArrayType *array =
+ // llvm::cast<clang::ConstantArrayType>(parent_qual_type.getTypePtr());
+ // const uint64_t element_count =
+ // array->getSize().getLimitedValue();
+ //
+ // if (idx < element_count)
+ // {
+ // std::pair<uint64_t, unsigned> field_type_info =
+ // ast->getTypeInfo(array->getElementType());
+ //
+ // char element_name[32];
+ // ::snprintf (element_name, sizeof (element_name),
+ // "%s[%u]", parent_name ? parent_name : "", idx);
+ //
+ // child_name.assign(element_name);
+ // assert(field_type_info.first % 8 == 0);
+ // child_byte_size = field_type_info.first / 8;
+ // child_byte_offset = idx * child_byte_size;
+ // return array->getElementType().getAsOpaquePtr();
+ // }
+ } break;
+
+ // case clang::Type::MemberPointerType:
+ // {
+ // MemberPointerType *mem_ptr_type =
+ // llvm::cast<MemberPointerType>(qual_type.getTypePtr());
+ // clang::QualType pointee_type =
+ // mem_ptr_type->getPointeeType();
+ //
+ // if (ClangASTContext::IsAggregateType
+ // (pointee_type.getAsOpaquePtr()))
+ // {
+ // return GetIndexOfChildWithName (ast,
+ // mem_ptr_type->getPointeeType().getAsOpaquePtr(),
+ // name);
+ // }
+ // }
+ // break;
+ //
+ case clang::Type::LValueReference:
+ case clang::Type::RValueReference: {
+ const clang::ReferenceType *reference_type =
+ llvm::cast<clang::ReferenceType>(qual_type.getTypePtr());
+ CompilerType pointee_type(getASTContext(),
+ reference_type->getPointeeType());
+
+ if (pointee_type.IsAggregateType()) {
+ return pointee_type.GetIndexOfChildWithName(name,
+ omit_empty_base_classes);
+ }
+ } break;
+
+ case clang::Type::Pointer: {
+ const clang::PointerType *pointer_type =
+ llvm::cast<clang::PointerType>(qual_type.getTypePtr());
+ CompilerType pointee_type(getASTContext(),
+ pointer_type->getPointeeType());
+
+ if (pointee_type.IsAggregateType()) {
+ return pointee_type.GetIndexOfChildWithName(name,
+ omit_empty_base_classes);
+ } else {
+ // if (parent_name)
+ // {
+ // child_name.assign(1, '*');
+ // child_name += parent_name;
+ // }
+ //
+ // // We have a pointer to an simple type
+ // if (idx == 0)
+ // {
+ // std::pair<uint64_t, unsigned> clang_type_info
+ // = ast->getTypeInfo(pointee_type);
+ // assert(clang_type_info.first % 8 == 0);
+ // child_byte_size = clang_type_info.first / 8;
+ // child_byte_offset = 0;
+ // return pointee_type.getAsOpaquePtr();
+ // }
+ }
+ } break;
+
+ case clang::Type::Auto:
+ return CompilerType(
+ getASTContext(),
+ llvm::cast<clang::AutoType>(qual_type)->getDeducedType())
+ .GetIndexOfChildWithName(name, omit_empty_base_classes);
+
+ case clang::Type::Elaborated:
+ return CompilerType(
+ getASTContext(),
+ llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType())
+ .GetIndexOfChildWithName(name, omit_empty_base_classes);
+
+ case clang::Type::Paren:
+ return CompilerType(getASTContext(),
+ llvm::cast<clang::ParenType>(qual_type)->desugar())
+ .GetIndexOfChildWithName(name, omit_empty_base_classes);
+
+ case clang::Type::Typedef:
+ return CompilerType(getASTContext(),
+ llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType())
+ .GetIndexOfChildWithName(name, omit_empty_base_classes);
- return 0;
+ default:
+ break;
+ }
+ }
+ return UINT32_MAX;
}
-CompilerType
-ClangASTContext::GetTemplateArgument (lldb::opaque_compiler_type_t type, size_t arg_idx, lldb::TemplateArgumentKind &kind)
-{
- if (!type)
- return CompilerType();
+size_t
+ClangASTContext::GetNumTemplateArguments(lldb::opaque_compiler_type_t type) {
+ if (!type)
+ return 0;
- clang::QualType qual_type (GetCanonicalQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Record:
- if (GetCompleteType(type))
- {
- const clang::CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
- if (cxx_record_decl)
- {
- const clang::ClassTemplateSpecializationDecl *template_decl = llvm::dyn_cast<clang::ClassTemplateSpecializationDecl>(cxx_record_decl);
- if (template_decl && arg_idx < template_decl->getTemplateArgs().size())
- {
- const clang::TemplateArgument &template_arg = template_decl->getTemplateArgs()[arg_idx];
- switch (template_arg.getKind())
- {
- case clang::TemplateArgument::Null:
- kind = eTemplateArgumentKindNull;
- return CompilerType();
-
- case clang::TemplateArgument::Type:
- kind = eTemplateArgumentKindType;
- return CompilerType(getASTContext(), template_arg.getAsType());
-
- case clang::TemplateArgument::Declaration:
- kind = eTemplateArgumentKindDeclaration;
- return CompilerType();
-
- case clang::TemplateArgument::Integral:
- kind = eTemplateArgumentKindIntegral;
- return CompilerType(getASTContext(), template_arg.getIntegralType());
-
- case clang::TemplateArgument::Template:
- kind = eTemplateArgumentKindTemplate;
- return CompilerType();
-
- case clang::TemplateArgument::TemplateExpansion:
- kind = eTemplateArgumentKindTemplateExpansion;
- return CompilerType();
-
- case clang::TemplateArgument::Expression:
- kind = eTemplateArgumentKindExpression;
- return CompilerType();
-
- case clang::TemplateArgument::Pack:
- kind = eTemplateArgumentKindPack;
- return CompilerType();
-
- default:
- assert (!"Unhandled clang::TemplateArgument::ArgKind");
- break;
- }
- }
- }
- }
- break;
-
- case clang::Type::Typedef:
- return (CompilerType (getASTContext(), llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType())).GetTemplateArgument(arg_idx, kind);
-
- case clang::Type::Auto:
- return (CompilerType (getASTContext(), llvm::cast<clang::AutoType>(qual_type)->getDeducedType())).GetTemplateArgument(arg_idx, kind);
-
- case clang::Type::Elaborated:
- return (CompilerType (getASTContext(), llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType())).GetTemplateArgument(arg_idx, kind);
-
- case clang::Type::Paren:
- return (CompilerType (getASTContext(), llvm::cast<clang::ParenType>(qual_type)->desugar())).GetTemplateArgument(arg_idx, kind);
-
- default:
- break;
- }
- kind = eTemplateArgumentKindNull;
- return CompilerType ();
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Record:
+ if (GetCompleteType(type)) {
+ const clang::CXXRecordDecl *cxx_record_decl =
+ qual_type->getAsCXXRecordDecl();
+ if (cxx_record_decl) {
+ const clang::ClassTemplateSpecializationDecl *template_decl =
+ llvm::dyn_cast<clang::ClassTemplateSpecializationDecl>(
+ cxx_record_decl);
+ if (template_decl)
+ return template_decl->getTemplateArgs().size();
+ }
+ }
+ break;
+
+ case clang::Type::Typedef:
+ return (CompilerType(getASTContext(),
+ llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()))
+ .GetNumTemplateArguments();
+
+ case clang::Type::Auto:
+ return (CompilerType(
+ getASTContext(),
+ llvm::cast<clang::AutoType>(qual_type)->getDeducedType()))
+ .GetNumTemplateArguments();
+
+ case clang::Type::Elaborated:
+ return (CompilerType(
+ getASTContext(),
+ llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType()))
+ .GetNumTemplateArguments();
+
+ case clang::Type::Paren:
+ return (CompilerType(getASTContext(),
+ llvm::cast<clang::ParenType>(qual_type)->desugar()))
+ .GetNumTemplateArguments();
+
+ default:
+ break;
+ }
+
+ return 0;
}
CompilerType
-ClangASTContext::GetTypeForFormatters (void* type)
-{
- if (type)
- return ClangUtil::RemoveFastQualifiers(CompilerType(this, type));
+ClangASTContext::GetTemplateArgument(lldb::opaque_compiler_type_t type,
+ size_t arg_idx,
+ lldb::TemplateArgumentKind &kind) {
+ if (!type)
return CompilerType();
-}
-clang::EnumDecl *
-ClangASTContext::GetAsEnumDecl (const CompilerType& type)
-{
- const clang::EnumType *enutype = llvm::dyn_cast<clang::EnumType>(ClangUtil::GetCanonicalQualType(type));
- if (enutype)
- return enutype->getDecl();
- return NULL;
-}
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Record:
+ if (GetCompleteType(type)) {
+ const clang::CXXRecordDecl *cxx_record_decl =
+ qual_type->getAsCXXRecordDecl();
+ if (cxx_record_decl) {
+ const clang::ClassTemplateSpecializationDecl *template_decl =
+ llvm::dyn_cast<clang::ClassTemplateSpecializationDecl>(
+ cxx_record_decl);
+ if (template_decl &&
+ arg_idx < template_decl->getTemplateArgs().size()) {
+ const clang::TemplateArgument &template_arg =
+ template_decl->getTemplateArgs()[arg_idx];
+ switch (template_arg.getKind()) {
+ case clang::TemplateArgument::Null:
+ kind = eTemplateArgumentKindNull;
+ return CompilerType();
-clang::RecordDecl *
-ClangASTContext::GetAsRecordDecl (const CompilerType& type)
-{
- const clang::RecordType *record_type = llvm::dyn_cast<clang::RecordType>(ClangUtil::GetCanonicalQualType(type));
- if (record_type)
- return record_type->getDecl();
- return nullptr;
-}
+ case clang::TemplateArgument::Type:
+ kind = eTemplateArgumentKindType;
+ return CompilerType(getASTContext(), template_arg.getAsType());
-clang::TagDecl *
-ClangASTContext::GetAsTagDecl (const CompilerType& type)
-{
- clang::QualType qual_type = ClangUtil::GetCanonicalQualType(type);
- if (qual_type.isNull())
- return nullptr;
- else
- return qual_type->getAsTagDecl();
+ case clang::TemplateArgument::Declaration:
+ kind = eTemplateArgumentKindDeclaration;
+ return CompilerType();
+
+ case clang::TemplateArgument::Integral:
+ kind = eTemplateArgumentKindIntegral;
+ return CompilerType(getASTContext(),
+ template_arg.getIntegralType());
+
+ case clang::TemplateArgument::Template:
+ kind = eTemplateArgumentKindTemplate;
+ return CompilerType();
+
+ case clang::TemplateArgument::TemplateExpansion:
+ kind = eTemplateArgumentKindTemplateExpansion;
+ return CompilerType();
+
+ case clang::TemplateArgument::Expression:
+ kind = eTemplateArgumentKindExpression;
+ return CompilerType();
+
+ case clang::TemplateArgument::Pack:
+ kind = eTemplateArgumentKindPack;
+ return CompilerType();
+
+ default:
+ assert(!"Unhandled clang::TemplateArgument::ArgKind");
+ break;
+ }
+ }
+ }
+ }
+ break;
+
+ case clang::Type::Typedef:
+ return (CompilerType(getASTContext(),
+ llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()))
+ .GetTemplateArgument(arg_idx, kind);
+
+ case clang::Type::Auto:
+ return (CompilerType(
+ getASTContext(),
+ llvm::cast<clang::AutoType>(qual_type)->getDeducedType()))
+ .GetTemplateArgument(arg_idx, kind);
+
+ case clang::Type::Elaborated:
+ return (CompilerType(
+ getASTContext(),
+ llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType()))
+ .GetTemplateArgument(arg_idx, kind);
+
+ case clang::Type::Paren:
+ return (CompilerType(getASTContext(),
+ llvm::cast<clang::ParenType>(qual_type)->desugar()))
+ .GetTemplateArgument(arg_idx, kind);
+
+ default:
+ break;
+ }
+ kind = eTemplateArgumentKindNull;
+ return CompilerType();
+}
+
+CompilerType ClangASTContext::GetTypeForFormatters(void *type) {
+ if (type)
+ return ClangUtil::RemoveFastQualifiers(CompilerType(this, type));
+ return CompilerType();
+}
+
+clang::EnumDecl *ClangASTContext::GetAsEnumDecl(const CompilerType &type) {
+ const clang::EnumType *enutype =
+ llvm::dyn_cast<clang::EnumType>(ClangUtil::GetCanonicalQualType(type));
+ if (enutype)
+ return enutype->getDecl();
+ return NULL;
+}
+
+clang::RecordDecl *ClangASTContext::GetAsRecordDecl(const CompilerType &type) {
+ const clang::RecordType *record_type =
+ llvm::dyn_cast<clang::RecordType>(ClangUtil::GetCanonicalQualType(type));
+ if (record_type)
+ return record_type->getDecl();
+ return nullptr;
+}
+
+clang::TagDecl *ClangASTContext::GetAsTagDecl(const CompilerType &type) {
+ clang::QualType qual_type = ClangUtil::GetCanonicalQualType(type);
+ if (qual_type.isNull())
+ return nullptr;
+ else
+ return qual_type->getAsTagDecl();
}
clang::CXXRecordDecl *
-ClangASTContext::GetAsCXXRecordDecl (lldb::opaque_compiler_type_t type)
-{
- return GetCanonicalQualType(type)->getAsCXXRecordDecl();
+ClangASTContext::GetAsCXXRecordDecl(lldb::opaque_compiler_type_t type) {
+ return GetCanonicalQualType(type)->getAsCXXRecordDecl();
}
clang::ObjCInterfaceDecl *
-ClangASTContext::GetAsObjCInterfaceDecl (const CompilerType& type)
-{
- const clang::ObjCObjectType *objc_class_type =
- llvm::dyn_cast<clang::ObjCObjectType>(ClangUtil::GetCanonicalQualType(type));
- if (objc_class_type)
- return objc_class_type->getInterface();
+ClangASTContext::GetAsObjCInterfaceDecl(const CompilerType &type) {
+ const clang::ObjCObjectType *objc_class_type =
+ llvm::dyn_cast<clang::ObjCObjectType>(
+ ClangUtil::GetCanonicalQualType(type));
+ if (objc_class_type)
+ return objc_class_type->getInterface();
+ return nullptr;
+}
+
+clang::FieldDecl *ClangASTContext::AddFieldToRecordType(
+ const CompilerType &type, const char *name,
+ const CompilerType &field_clang_type, AccessType access,
+ uint32_t bitfield_bit_size) {
+ if (!type.IsValid() || !field_clang_type.IsValid())
return nullptr;
-}
+ ClangASTContext *ast =
+ llvm::dyn_cast_or_null<ClangASTContext>(type.GetTypeSystem());
+ if (!ast)
+ return nullptr;
+ clang::ASTContext *clang_ast = ast->getASTContext();
+
+ clang::FieldDecl *field = nullptr;
+
+ clang::Expr *bit_width = nullptr;
+ if (bitfield_bit_size != 0) {
+ llvm::APInt bitfield_bit_size_apint(
+ clang_ast->getTypeSize(clang_ast->IntTy), bitfield_bit_size);
+ bit_width = new (*clang_ast)
+ clang::IntegerLiteral(*clang_ast, bitfield_bit_size_apint,
+ clang_ast->IntTy, clang::SourceLocation());
+ }
+
+ clang::RecordDecl *record_decl = ast->GetAsRecordDecl(type);
+ if (record_decl) {
+ field = clang::FieldDecl::Create(
+ *clang_ast, record_decl, clang::SourceLocation(),
+ clang::SourceLocation(),
+ name ? &clang_ast->Idents.get(name) : nullptr, // Identifier
+ ClangUtil::GetQualType(field_clang_type), // Field type
+ nullptr, // TInfo *
+ bit_width, // BitWidth
+ false, // Mutable
+ clang::ICIS_NoInit); // HasInit
+
+ if (!name) {
+ // Determine whether this field corresponds to an anonymous
+ // struct or union.
+ if (const clang::TagType *TagT =
+ field->getType()->getAs<clang::TagType>()) {
+ if (clang::RecordDecl *Rec =
+ llvm::dyn_cast<clang::RecordDecl>(TagT->getDecl()))
+ if (!Rec->getDeclName()) {
+ Rec->setAnonymousStructOrUnion(true);
+ field->setImplicit();
+ }
+ }
+ }
+
+ if (field) {
+ field->setAccess(
+ ClangASTContext::ConvertAccessTypeToAccessSpecifier(access));
+
+ record_decl->addDecl(field);
-clang::FieldDecl *
-ClangASTContext::AddFieldToRecordType (const CompilerType& type, const char *name,
- const CompilerType &field_clang_type,
- AccessType access,
- uint32_t bitfield_bit_size)
-{
- if (!type.IsValid() || !field_clang_type.IsValid())
- return nullptr;
- ClangASTContext *ast = llvm::dyn_cast_or_null<ClangASTContext>(type.GetTypeSystem());
- if (!ast)
- return nullptr;
- clang::ASTContext* clang_ast = ast->getASTContext();
-
- clang::FieldDecl *field = nullptr;
-
- clang::Expr *bit_width = nullptr;
- if (bitfield_bit_size != 0)
- {
- llvm::APInt bitfield_bit_size_apint(clang_ast->getTypeSize(clang_ast->IntTy), bitfield_bit_size);
- bit_width = new (*clang_ast)clang::IntegerLiteral (*clang_ast, bitfield_bit_size_apint, clang_ast->IntTy, clang::SourceLocation());
- }
-
- clang::RecordDecl *record_decl = ast->GetAsRecordDecl (type);
- if (record_decl)
- {
- field = clang::FieldDecl::Create(*clang_ast, record_decl, clang::SourceLocation(), clang::SourceLocation(),
- name ? &clang_ast->Idents.get(name) : nullptr, // Identifier
- ClangUtil::GetQualType(field_clang_type), // Field type
- nullptr, // TInfo *
- bit_width, // BitWidth
- false, // Mutable
- clang::ICIS_NoInit); // HasInit
-
- if (!name)
- {
- // Determine whether this field corresponds to an anonymous
- // struct or union.
- if (const clang::TagType *TagT = field->getType()->getAs<clang::TagType>()) {
- if (clang::RecordDecl *Rec = llvm::dyn_cast<clang::RecordDecl>(TagT->getDecl()))
- if (!Rec->getDeclName()) {
- Rec->setAnonymousStructOrUnion(true);
- field->setImplicit();
-
- }
- }
- }
-
- if (field)
- {
- field->setAccess (ClangASTContext::ConvertAccessTypeToAccessSpecifier (access));
-
- record_decl->addDecl(field);
-
#ifdef LLDB_CONFIGURATION_DEBUG
- VerifyDecl(field);
+ VerifyDecl(field);
#endif
- }
}
- else
- {
- clang::ObjCInterfaceDecl *class_interface_decl = ast->GetAsObjCInterfaceDecl (type);
-
- if (class_interface_decl)
- {
- const bool is_synthesized = false;
-
- field_clang_type.GetCompleteType();
-
- field = clang::ObjCIvarDecl::Create(
- *clang_ast, class_interface_decl, clang::SourceLocation(), clang::SourceLocation(),
- name ? &clang_ast->Idents.get(name) : nullptr, // Identifier
- ClangUtil::GetQualType(field_clang_type), // Field type
- nullptr, // TypeSourceInfo *
- ConvertAccessTypeToObjCIvarAccessControl(access), bit_width, is_synthesized);
-
- if (field)
- {
- class_interface_decl->addDecl(field);
-
+ } else {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ ast->GetAsObjCInterfaceDecl(type);
+
+ if (class_interface_decl) {
+ const bool is_synthesized = false;
+
+ field_clang_type.GetCompleteType();
+
+ field = clang::ObjCIvarDecl::Create(
+ *clang_ast, class_interface_decl, clang::SourceLocation(),
+ clang::SourceLocation(),
+ name ? &clang_ast->Idents.get(name) : nullptr, // Identifier
+ ClangUtil::GetQualType(field_clang_type), // Field type
+ nullptr, // TypeSourceInfo *
+ ConvertAccessTypeToObjCIvarAccessControl(access), bit_width,
+ is_synthesized);
+
+ if (field) {
+ class_interface_decl->addDecl(field);
+
#ifdef LLDB_CONFIGURATION_DEBUG
- VerifyDecl(field);
+ VerifyDecl(field);
#endif
- }
+ }
+ }
+ }
+ return field;
+}
+
+void ClangASTContext::BuildIndirectFields(const CompilerType &type) {
+ if (!type)
+ return;
+
+ ClangASTContext *ast = llvm::dyn_cast<ClangASTContext>(type.GetTypeSystem());
+ if (!ast)
+ return;
+
+ clang::RecordDecl *record_decl = ast->GetAsRecordDecl(type);
+
+ if (!record_decl)
+ return;
+
+ typedef llvm::SmallVector<clang::IndirectFieldDecl *, 1> IndirectFieldVector;
+
+ IndirectFieldVector indirect_fields;
+ clang::RecordDecl::field_iterator field_pos;
+ clang::RecordDecl::field_iterator field_end_pos = record_decl->field_end();
+ clang::RecordDecl::field_iterator last_field_pos = field_end_pos;
+ for (field_pos = record_decl->field_begin(); field_pos != field_end_pos;
+ last_field_pos = field_pos++) {
+ if (field_pos->isAnonymousStructOrUnion()) {
+ clang::QualType field_qual_type = field_pos->getType();
+
+ const clang::RecordType *field_record_type =
+ field_qual_type->getAs<clang::RecordType>();
+
+ if (!field_record_type)
+ continue;
+
+ clang::RecordDecl *field_record_decl = field_record_type->getDecl();
+
+ if (!field_record_decl)
+ continue;
+
+ for (clang::RecordDecl::decl_iterator
+ di = field_record_decl->decls_begin(),
+ de = field_record_decl->decls_end();
+ di != de; ++di) {
+ if (clang::FieldDecl *nested_field_decl =
+ llvm::dyn_cast<clang::FieldDecl>(*di)) {
+ clang::NamedDecl **chain =
+ new (*ast->getASTContext()) clang::NamedDecl *[2];
+ chain[0] = *field_pos;
+ chain[1] = nested_field_decl;
+ clang::IndirectFieldDecl *indirect_field =
+ clang::IndirectFieldDecl::Create(
+ *ast->getASTContext(), record_decl, clang::SourceLocation(),
+ nested_field_decl->getIdentifier(),
+ nested_field_decl->getType(), {chain, 2});
+
+ indirect_field->setImplicit();
+
+ indirect_field->setAccess(ClangASTContext::UnifyAccessSpecifiers(
+ field_pos->getAccess(), nested_field_decl->getAccess()));
+
+ indirect_fields.push_back(indirect_field);
+ } else if (clang::IndirectFieldDecl *nested_indirect_field_decl =
+ llvm::dyn_cast<clang::IndirectFieldDecl>(*di)) {
+ size_t nested_chain_size =
+ nested_indirect_field_decl->getChainingSize();
+ clang::NamedDecl **chain = new (*ast->getASTContext())
+ clang::NamedDecl *[nested_chain_size + 1];
+ chain[0] = *field_pos;
+
+ int chain_index = 1;
+ for (clang::IndirectFieldDecl::chain_iterator
+ nci = nested_indirect_field_decl->chain_begin(),
+ nce = nested_indirect_field_decl->chain_end();
+ nci < nce; ++nci) {
+ chain[chain_index] = *nci;
+ chain_index++;
+ }
+
+ clang::IndirectFieldDecl *indirect_field =
+ clang::IndirectFieldDecl::Create(
+ *ast->getASTContext(), record_decl, clang::SourceLocation(),
+ nested_indirect_field_decl->getIdentifier(),
+ nested_indirect_field_decl->getType(),
+ {chain, nested_chain_size + 1});
+
+ indirect_field->setImplicit();
+
+ indirect_field->setAccess(ClangASTContext::UnifyAccessSpecifiers(
+ field_pos->getAccess(), nested_indirect_field_decl->getAccess()));
+
+ indirect_fields.push_back(indirect_field);
}
+ }
}
- return field;
+ }
+
+ // Check the last field to see if it has an incomplete array type as its
+ // last member and if it does, the tell the record decl about it
+ if (last_field_pos != field_end_pos) {
+ if (last_field_pos->getType()->isIncompleteArrayType())
+ record_decl->hasFlexibleArrayMember();
+ }
+
+ for (IndirectFieldVector::iterator ifi = indirect_fields.begin(),
+ ife = indirect_fields.end();
+ ifi < ife; ++ifi) {
+ record_decl->addDecl(*ifi);
+ }
}
-void
-ClangASTContext::BuildIndirectFields (const CompilerType& type)
-{
- if (!type)
- return;
+void ClangASTContext::SetIsPacked(const CompilerType &type) {
+ if (type) {
+ ClangASTContext *ast =
+ llvm::dyn_cast<ClangASTContext>(type.GetTypeSystem());
+ if (ast) {
+ clang::RecordDecl *record_decl = GetAsRecordDecl(type);
- ClangASTContext *ast = llvm::dyn_cast<ClangASTContext>(type.GetTypeSystem());
- if (!ast)
+ if (!record_decl)
return;
- clang::RecordDecl *record_decl = ast->GetAsRecordDecl(type);
-
- if (!record_decl)
- return;
-
- typedef llvm::SmallVector <clang::IndirectFieldDecl *, 1> IndirectFieldVector;
-
- IndirectFieldVector indirect_fields;
- clang::RecordDecl::field_iterator field_pos;
- clang::RecordDecl::field_iterator field_end_pos = record_decl->field_end();
- clang::RecordDecl::field_iterator last_field_pos = field_end_pos;
- for (field_pos = record_decl->field_begin(); field_pos != field_end_pos; last_field_pos = field_pos++)
- {
- if (field_pos->isAnonymousStructOrUnion())
- {
- clang::QualType field_qual_type = field_pos->getType();
-
- const clang::RecordType *field_record_type = field_qual_type->getAs<clang::RecordType>();
-
- if (!field_record_type)
- continue;
-
- clang::RecordDecl *field_record_decl = field_record_type->getDecl();
-
- if (!field_record_decl)
- continue;
-
- for (clang::RecordDecl::decl_iterator di = field_record_decl->decls_begin(), de = field_record_decl->decls_end();
- di != de;
- ++di)
- {
- if (clang::FieldDecl *nested_field_decl = llvm::dyn_cast<clang::FieldDecl>(*di))
- {
- clang::NamedDecl **chain = new (*ast->getASTContext()) clang::NamedDecl*[2];
- chain[0] = *field_pos;
- chain[1] = nested_field_decl;
- clang::IndirectFieldDecl *indirect_field = clang::IndirectFieldDecl::Create(*ast->getASTContext(),
- record_decl,
- clang::SourceLocation(),
- nested_field_decl->getIdentifier(),
- nested_field_decl->getType(),
- {chain, 2});
-
- indirect_field->setImplicit();
-
- indirect_field->setAccess(ClangASTContext::UnifyAccessSpecifiers(field_pos->getAccess(),
- nested_field_decl->getAccess()));
-
- indirect_fields.push_back(indirect_field);
- }
- else if (clang::IndirectFieldDecl *nested_indirect_field_decl = llvm::dyn_cast<clang::IndirectFieldDecl>(*di))
- {
- size_t nested_chain_size = nested_indirect_field_decl->getChainingSize();
- clang::NamedDecl **chain = new (*ast->getASTContext()) clang::NamedDecl*[nested_chain_size + 1];
- chain[0] = *field_pos;
-
- int chain_index = 1;
- for (clang::IndirectFieldDecl::chain_iterator nci = nested_indirect_field_decl->chain_begin(),
- nce = nested_indirect_field_decl->chain_end();
- nci < nce;
- ++nci)
- {
- chain[chain_index] = *nci;
- chain_index++;
- }
-
- clang::IndirectFieldDecl *indirect_field = clang::IndirectFieldDecl::Create(*ast->getASTContext(),
- record_decl,
- clang::SourceLocation(),
- nested_indirect_field_decl->getIdentifier(),
- nested_indirect_field_decl->getType(),
- {chain, nested_chain_size + 1});
-
- indirect_field->setImplicit();
-
- indirect_field->setAccess(ClangASTContext::UnifyAccessSpecifiers(field_pos->getAccess(),
- nested_indirect_field_decl->getAccess()));
-
- indirect_fields.push_back(indirect_field);
- }
- }
- }
- }
-
- // Check the last field to see if it has an incomplete array type as its
- // last member and if it does, the tell the record decl about it
- if (last_field_pos != field_end_pos)
- {
- if (last_field_pos->getType()->isIncompleteArrayType())
- record_decl->hasFlexibleArrayMember();
- }
-
- for (IndirectFieldVector::iterator ifi = indirect_fields.begin(), ife = indirect_fields.end();
- ifi < ife;
- ++ifi)
- {
- record_decl->addDecl(*ifi);
- }
-}
-
-void
-ClangASTContext::SetIsPacked (const CompilerType& type)
-{
- if (type)
- {
- ClangASTContext *ast = llvm::dyn_cast<ClangASTContext>(type.GetTypeSystem());
- if (ast)
- {
- clang::RecordDecl *record_decl = GetAsRecordDecl(type);
-
- if (!record_decl)
- return;
-
- record_decl->addAttr(clang::PackedAttr::CreateImplicit(*ast->getASTContext()));
- }
+ record_decl->addAttr(
+ clang::PackedAttr::CreateImplicit(*ast->getASTContext()));
}
+ }
}
-clang::VarDecl *
-ClangASTContext::AddVariableToRecordType (const CompilerType& type, const char *name,
- const CompilerType &var_type,
- AccessType access)
-{
- clang::VarDecl *var_decl = nullptr;
-
- if (!type.IsValid() || !var_type.IsValid())
- return nullptr;
- ClangASTContext *ast = llvm::dyn_cast<ClangASTContext>(type.GetTypeSystem());
- if (!ast)
- return nullptr;
-
- clang::RecordDecl *record_decl = ast->GetAsRecordDecl (type);
- if (record_decl)
- {
- var_decl =
- clang::VarDecl::Create(*ast->getASTContext(), // ASTContext &
- record_decl, // DeclContext *
- clang::SourceLocation(), // clang::SourceLocation StartLoc
- clang::SourceLocation(), // clang::SourceLocation IdLoc
- name ? &ast->getASTContext()->Idents.get(name) : nullptr, // clang::IdentifierInfo *
- ClangUtil::GetQualType(var_type), // Variable clang::QualType
- nullptr, // TypeSourceInfo *
- clang::SC_Static); // StorageClass
- if (var_decl)
- {
- var_decl->setAccess(ClangASTContext::ConvertAccessTypeToAccessSpecifier (access));
- record_decl->addDecl(var_decl);
-
+clang::VarDecl *ClangASTContext::AddVariableToRecordType(
+ const CompilerType &type, const char *name, const CompilerType &var_type,
+ AccessType access) {
+ clang::VarDecl *var_decl = nullptr;
+
+ if (!type.IsValid() || !var_type.IsValid())
+ return nullptr;
+ ClangASTContext *ast = llvm::dyn_cast<ClangASTContext>(type.GetTypeSystem());
+ if (!ast)
+ return nullptr;
+
+ clang::RecordDecl *record_decl = ast->GetAsRecordDecl(type);
+ if (record_decl) {
+ var_decl = clang::VarDecl::Create(
+ *ast->getASTContext(), // ASTContext &
+ record_decl, // DeclContext *
+ clang::SourceLocation(), // clang::SourceLocation StartLoc
+ clang::SourceLocation(), // clang::SourceLocation IdLoc
+ name ? &ast->getASTContext()->Idents.get(name)
+ : nullptr, // clang::IdentifierInfo *
+ ClangUtil::GetQualType(var_type), // Variable clang::QualType
+ nullptr, // TypeSourceInfo *
+ clang::SC_Static); // StorageClass
+ if (var_decl) {
+ var_decl->setAccess(
+ ClangASTContext::ConvertAccessTypeToAccessSpecifier(access));
+ record_decl->addDecl(var_decl);
+
#ifdef LLDB_CONFIGURATION_DEBUG
- VerifyDecl(var_decl);
+ VerifyDecl(var_decl);
#endif
- }
}
- return var_decl;
+ }
+ return var_decl;
}
+clang::CXXMethodDecl *ClangASTContext::AddMethodToCXXRecordType(
+ lldb::opaque_compiler_type_t type, const char *name,
+ const CompilerType &method_clang_type, lldb::AccessType access,
+ bool is_virtual, bool is_static, bool is_inline, bool is_explicit,
+ bool is_attr_used, bool is_artificial) {
+ if (!type || !method_clang_type.IsValid() || name == nullptr ||
+ name[0] == '\0')
+ return nullptr;
+
+ clang::QualType record_qual_type(GetCanonicalQualType(type));
+
+ clang::CXXRecordDecl *cxx_record_decl =
+ record_qual_type->getAsCXXRecordDecl();
+
+ if (cxx_record_decl == nullptr)
+ return nullptr;
+
+ clang::QualType method_qual_type(ClangUtil::GetQualType(method_clang_type));
+
+ clang::CXXMethodDecl *cxx_method_decl = nullptr;
+
+ clang::DeclarationName decl_name(&getASTContext()->Idents.get(name));
+
+ const clang::FunctionType *function_type =
+ llvm::dyn_cast<clang::FunctionType>(method_qual_type.getTypePtr());
+
+ if (function_type == nullptr)
+ return nullptr;
+
+ const clang::FunctionProtoType *method_function_prototype(
+ llvm::dyn_cast<clang::FunctionProtoType>(function_type));
+
+ if (!method_function_prototype)
+ return nullptr;
+
+ unsigned int num_params = method_function_prototype->getNumParams();
+
+ clang::CXXDestructorDecl *cxx_dtor_decl(nullptr);
+ clang::CXXConstructorDecl *cxx_ctor_decl(nullptr);
+
+ if (is_artificial)
+ return nullptr; // skip everything artificial
+
+ if (name[0] == '~') {
+ cxx_dtor_decl = clang::CXXDestructorDecl::Create(
+ *getASTContext(), cxx_record_decl, clang::SourceLocation(),
+ clang::DeclarationNameInfo(
+ getASTContext()->DeclarationNames.getCXXDestructorName(
+ getASTContext()->getCanonicalType(record_qual_type)),
+ clang::SourceLocation()),
+ method_qual_type, nullptr, is_inline, is_artificial);
+ cxx_method_decl = cxx_dtor_decl;
+ } else if (decl_name == cxx_record_decl->getDeclName()) {
+ cxx_ctor_decl = clang::CXXConstructorDecl::Create(
+ *getASTContext(), cxx_record_decl, clang::SourceLocation(),
+ clang::DeclarationNameInfo(
+ getASTContext()->DeclarationNames.getCXXConstructorName(
+ getASTContext()->getCanonicalType(record_qual_type)),
+ clang::SourceLocation()),
+ method_qual_type,
+ nullptr, // TypeSourceInfo *
+ is_explicit, is_inline, is_artificial, false /*is_constexpr*/);
+ cxx_method_decl = cxx_ctor_decl;
+ } else {
+ clang::StorageClass SC = is_static ? clang::SC_Static : clang::SC_None;
+ clang::OverloadedOperatorKind op_kind = clang::NUM_OVERLOADED_OPERATORS;
+
+ if (IsOperator(name, op_kind)) {
+ if (op_kind != clang::NUM_OVERLOADED_OPERATORS) {
+ // Check the number of operator parameters. Sometimes we have
+ // seen bad DWARF that doesn't correctly describe operators and
+ // if we try to create a method and add it to the class, clang
+ // will assert and crash, so we need to make sure things are
+ // acceptable.
+ const bool is_method = true;
+ if (!ClangASTContext::CheckOverloadedOperatorKindParameterCount(
+ is_method, op_kind, num_params))
+ return nullptr;
+ cxx_method_decl = clang::CXXMethodDecl::Create(
+ *getASTContext(), cxx_record_decl, clang::SourceLocation(),
+ clang::DeclarationNameInfo(
+ getASTContext()->DeclarationNames.getCXXOperatorName(op_kind),
+ clang::SourceLocation()),
+ method_qual_type,
+ nullptr, // TypeSourceInfo *
+ SC, is_inline, false /*is_constexpr*/, clang::SourceLocation());
+ } else if (num_params == 0) {
+ // Conversion operators don't take params...
+ cxx_method_decl = clang::CXXConversionDecl::Create(
+ *getASTContext(), cxx_record_decl, clang::SourceLocation(),
+ clang::DeclarationNameInfo(
+ getASTContext()->DeclarationNames.getCXXConversionFunctionName(
+ getASTContext()->getCanonicalType(
+ function_type->getReturnType())),
+ clang::SourceLocation()),
+ method_qual_type,
+ nullptr, // TypeSourceInfo *
+ is_inline, is_explicit, false /*is_constexpr*/,
+ clang::SourceLocation());
+ }
+ }
+
+ if (cxx_method_decl == nullptr) {
+ cxx_method_decl = clang::CXXMethodDecl::Create(
+ *getASTContext(), cxx_record_decl, clang::SourceLocation(),
+ clang::DeclarationNameInfo(decl_name, clang::SourceLocation()),
+ method_qual_type,
+ nullptr, // TypeSourceInfo *
+ SC, is_inline, false /*is_constexpr*/, clang::SourceLocation());
+ }
+ }
+
+ clang::AccessSpecifier access_specifier =
+ ClangASTContext::ConvertAccessTypeToAccessSpecifier(access);
+
+ cxx_method_decl->setAccess(access_specifier);
+ cxx_method_decl->setVirtualAsWritten(is_virtual);
+
+ if (is_attr_used)
+ cxx_method_decl->addAttr(clang::UsedAttr::CreateImplicit(*getASTContext()));
+
+ // Populate the method decl with parameter decls
+
+ llvm::SmallVector<clang::ParmVarDecl *, 12> params;
+
+ for (unsigned param_index = 0; param_index < num_params; ++param_index) {
+ params.push_back(clang::ParmVarDecl::Create(
+ *getASTContext(), cxx_method_decl, clang::SourceLocation(),
+ clang::SourceLocation(),
+ nullptr, // anonymous
+ method_function_prototype->getParamType(param_index), nullptr,
+ clang::SC_None, nullptr));
+ }
+
+ cxx_method_decl->setParams(llvm::ArrayRef<clang::ParmVarDecl *>(params));
+
+ cxx_record_decl->addDecl(cxx_method_decl);
+
+ // Sometimes the debug info will mention a constructor (default/copy/move),
+ // destructor, or assignment operator (copy/move) but there won't be any
+ // version of this in the code. So we check if the function was artificially
+ // generated and if it is trivial and this lets the compiler/backend know
+ // that it can inline the IR for these when it needs to and we can avoid a
+ // "missing function" error when running expressions.
+
+ if (is_artificial) {
+ if (cxx_ctor_decl && ((cxx_ctor_decl->isDefaultConstructor() &&
+ cxx_record_decl->hasTrivialDefaultConstructor()) ||
+ (cxx_ctor_decl->isCopyConstructor() &&
+ cxx_record_decl->hasTrivialCopyConstructor()) ||
+ (cxx_ctor_decl->isMoveConstructor() &&
+ cxx_record_decl->hasTrivialMoveConstructor()))) {
+ cxx_ctor_decl->setDefaulted();
+ cxx_ctor_decl->setTrivial(true);
+ } else if (cxx_dtor_decl) {
+ if (cxx_record_decl->hasTrivialDestructor()) {
+ cxx_dtor_decl->setDefaulted();
+ cxx_dtor_decl->setTrivial(true);
+ }
+ } else if ((cxx_method_decl->isCopyAssignmentOperator() &&
+ cxx_record_decl->hasTrivialCopyAssignment()) ||
+ (cxx_method_decl->isMoveAssignmentOperator() &&
+ cxx_record_decl->hasTrivialMoveAssignment())) {
+ cxx_method_decl->setDefaulted();
+ cxx_method_decl->setTrivial(true);
+ }
+ }
-clang::CXXMethodDecl *
-ClangASTContext::AddMethodToCXXRecordType (lldb::opaque_compiler_type_t type, const char *name,
- const CompilerType &method_clang_type,
- lldb::AccessType access,
- bool is_virtual,
- bool is_static,
- bool is_inline,
- bool is_explicit,
- bool is_attr_used,
- bool is_artificial)
-{
- if (!type || !method_clang_type.IsValid() || name == nullptr || name[0] == '\0')
- return nullptr;
-
- clang::QualType record_qual_type(GetCanonicalQualType(type));
-
- clang::CXXRecordDecl *cxx_record_decl = record_qual_type->getAsCXXRecordDecl();
-
- if (cxx_record_decl == nullptr)
- return nullptr;
-
- clang::QualType method_qual_type(ClangUtil::GetQualType(method_clang_type));
-
- clang::CXXMethodDecl *cxx_method_decl = nullptr;
-
- clang::DeclarationName decl_name (&getASTContext()->Idents.get(name));
-
- const clang::FunctionType *function_type = llvm::dyn_cast<clang::FunctionType>(method_qual_type.getTypePtr());
-
- if (function_type == nullptr)
- return nullptr;
-
- const clang::FunctionProtoType *method_function_prototype (llvm::dyn_cast<clang::FunctionProtoType>(function_type));
-
- if (!method_function_prototype)
- return nullptr;
-
- unsigned int num_params = method_function_prototype->getNumParams();
-
- clang::CXXDestructorDecl *cxx_dtor_decl(nullptr);
- clang::CXXConstructorDecl *cxx_ctor_decl(nullptr);
-
- if (is_artificial)
- return nullptr; // skip everything artificial
-
- if (name[0] == '~')
- {
- cxx_dtor_decl = clang::CXXDestructorDecl::Create (*getASTContext(),
- cxx_record_decl,
- clang::SourceLocation(),
- clang::DeclarationNameInfo (getASTContext()->DeclarationNames.getCXXDestructorName (getASTContext()->getCanonicalType (record_qual_type)), clang::SourceLocation()),
- method_qual_type,
- nullptr,
- is_inline,
- is_artificial);
- cxx_method_decl = cxx_dtor_decl;
- }
- else if (decl_name == cxx_record_decl->getDeclName())
- {
- cxx_ctor_decl = clang::CXXConstructorDecl::Create (*getASTContext(),
- cxx_record_decl,
- clang::SourceLocation(),
- clang::DeclarationNameInfo (getASTContext()->DeclarationNames.getCXXConstructorName (getASTContext()->getCanonicalType (record_qual_type)), clang::SourceLocation()),
- method_qual_type,
- nullptr, // TypeSourceInfo *
- is_explicit,
- is_inline,
- is_artificial,
- false /*is_constexpr*/);
- cxx_method_decl = cxx_ctor_decl;
- }
- else
- {
- clang::StorageClass SC = is_static ? clang::SC_Static : clang::SC_None;
- clang::OverloadedOperatorKind op_kind = clang::NUM_OVERLOADED_OPERATORS;
-
- if (IsOperator (name, op_kind))
- {
- if (op_kind != clang::NUM_OVERLOADED_OPERATORS)
- {
- // Check the number of operator parameters. Sometimes we have
- // seen bad DWARF that doesn't correctly describe operators and
- // if we try to create a method and add it to the class, clang
- // will assert and crash, so we need to make sure things are
- // acceptable.
- const bool is_method = true;
- if (!ClangASTContext::CheckOverloadedOperatorKindParameterCount(is_method, op_kind, num_params))
- return nullptr;
- cxx_method_decl = clang::CXXMethodDecl::Create (*getASTContext(),
- cxx_record_decl,
- clang::SourceLocation(),
- clang::DeclarationNameInfo (getASTContext()->DeclarationNames.getCXXOperatorName (op_kind), clang::SourceLocation()),
- method_qual_type,
- nullptr, // TypeSourceInfo *
- SC,
- is_inline,
- false /*is_constexpr*/,
- clang::SourceLocation());
- }
- else if (num_params == 0)
- {
- // Conversion operators don't take params...
- cxx_method_decl = clang::CXXConversionDecl::Create (*getASTContext(),
- cxx_record_decl,
- clang::SourceLocation(),
- clang::DeclarationNameInfo (getASTContext()->DeclarationNames.getCXXConversionFunctionName (getASTContext()->getCanonicalType (function_type->getReturnType())), clang::SourceLocation()),
- method_qual_type,
- nullptr, // TypeSourceInfo *
- is_inline,
- is_explicit,
- false /*is_constexpr*/,
- clang::SourceLocation());
- }
- }
-
- if (cxx_method_decl == nullptr)
- {
- cxx_method_decl = clang::CXXMethodDecl::Create (*getASTContext(),
- cxx_record_decl,
- clang::SourceLocation(),
- clang::DeclarationNameInfo (decl_name, clang::SourceLocation()),
- method_qual_type,
- nullptr, // TypeSourceInfo *
- SC,
- is_inline,
- false /*is_constexpr*/,
- clang::SourceLocation());
- }
- }
-
- clang::AccessSpecifier access_specifier = ClangASTContext::ConvertAccessTypeToAccessSpecifier (access);
-
- cxx_method_decl->setAccess (access_specifier);
- cxx_method_decl->setVirtualAsWritten (is_virtual);
-
- if (is_attr_used)
- cxx_method_decl->addAttr(clang::UsedAttr::CreateImplicit(*getASTContext()));
-
- // Populate the method decl with parameter decls
-
- llvm::SmallVector<clang::ParmVarDecl *, 12> params;
-
- for (unsigned param_index = 0;
- param_index < num_params;
- ++param_index)
- {
- params.push_back (clang::ParmVarDecl::Create (*getASTContext(),
- cxx_method_decl,
- clang::SourceLocation(),
- clang::SourceLocation(),
- nullptr, // anonymous
- method_function_prototype->getParamType(param_index),
- nullptr,
- clang::SC_None,
- nullptr));
- }
-
- cxx_method_decl->setParams (llvm::ArrayRef<clang::ParmVarDecl*>(params));
-
- cxx_record_decl->addDecl (cxx_method_decl);
-
- // Sometimes the debug info will mention a constructor (default/copy/move),
- // destructor, or assignment operator (copy/move) but there won't be any
- // version of this in the code. So we check if the function was artificially
- // generated and if it is trivial and this lets the compiler/backend know
- // that it can inline the IR for these when it needs to and we can avoid a
- // "missing function" error when running expressions.
-
- if (is_artificial)
- {
- if (cxx_ctor_decl &&
- ((cxx_ctor_decl->isDefaultConstructor() && cxx_record_decl->hasTrivialDefaultConstructor ()) ||
- (cxx_ctor_decl->isCopyConstructor() && cxx_record_decl->hasTrivialCopyConstructor ()) ||
- (cxx_ctor_decl->isMoveConstructor() && cxx_record_decl->hasTrivialMoveConstructor ()) ))
- {
- cxx_ctor_decl->setDefaulted();
- cxx_ctor_decl->setTrivial(true);
- }
- else if (cxx_dtor_decl)
- {
- if (cxx_record_decl->hasTrivialDestructor())
- {
- cxx_dtor_decl->setDefaulted();
- cxx_dtor_decl->setTrivial(true);
- }
- }
- else if ((cxx_method_decl->isCopyAssignmentOperator() && cxx_record_decl->hasTrivialCopyAssignment()) ||
- (cxx_method_decl->isMoveAssignmentOperator() && cxx_record_decl->hasTrivialMoveAssignment()))
- {
- cxx_method_decl->setDefaulted();
- cxx_method_decl->setTrivial(true);
- }
- }
-
#ifdef LLDB_CONFIGURATION_DEBUG
- VerifyDecl(cxx_method_decl);
+ VerifyDecl(cxx_method_decl);
#endif
-
- // printf ("decl->isPolymorphic() = %i\n", cxx_record_decl->isPolymorphic());
- // printf ("decl->isAggregate() = %i\n", cxx_record_decl->isAggregate());
- // printf ("decl->isPOD() = %i\n", cxx_record_decl->isPOD());
- // printf ("decl->isEmpty() = %i\n", cxx_record_decl->isEmpty());
- // printf ("decl->isAbstract() = %i\n", cxx_record_decl->isAbstract());
- // printf ("decl->hasTrivialConstructor() = %i\n", cxx_record_decl->hasTrivialConstructor());
- // printf ("decl->hasTrivialCopyConstructor() = %i\n", cxx_record_decl->hasTrivialCopyConstructor());
- // printf ("decl->hasTrivialCopyAssignment() = %i\n", cxx_record_decl->hasTrivialCopyAssignment());
- // printf ("decl->hasTrivialDestructor() = %i\n", cxx_record_decl->hasTrivialDestructor());
- return cxx_method_decl;
-}
+ // printf ("decl->isPolymorphic() = %i\n",
+ // cxx_record_decl->isPolymorphic());
+ // printf ("decl->isAggregate() = %i\n",
+ // cxx_record_decl->isAggregate());
+ // printf ("decl->isPOD() = %i\n",
+ // cxx_record_decl->isPOD());
+ // printf ("decl->isEmpty() = %i\n",
+ // cxx_record_decl->isEmpty());
+ // printf ("decl->isAbstract() = %i\n",
+ // cxx_record_decl->isAbstract());
+ // printf ("decl->hasTrivialConstructor() = %i\n",
+ // cxx_record_decl->hasTrivialConstructor());
+ // printf ("decl->hasTrivialCopyConstructor() = %i\n",
+ // cxx_record_decl->hasTrivialCopyConstructor());
+ // printf ("decl->hasTrivialCopyAssignment() = %i\n",
+ // cxx_record_decl->hasTrivialCopyAssignment());
+ // printf ("decl->hasTrivialDestructor() = %i\n",
+ // cxx_record_decl->hasTrivialDestructor());
+ return cxx_method_decl;
+}
#pragma mark C++ Base Classes
clang::CXXBaseSpecifier *
-ClangASTContext::CreateBaseClassSpecifier (lldb::opaque_compiler_type_t type, AccessType access, bool is_virtual, bool base_of_class)
-{
- if (type)
- return new clang::CXXBaseSpecifier (clang::SourceRange(),
- is_virtual,
- base_of_class,
- ClangASTContext::ConvertAccessTypeToAccessSpecifier (access),
- getASTContext()->getTrivialTypeSourceInfo (GetQualType(type)),
- clang::SourceLocation());
- return nullptr;
-}
-
-void
-ClangASTContext::DeleteBaseClassSpecifiers (clang::CXXBaseSpecifier **base_classes, unsigned num_base_classes)
-{
- for (unsigned i=0; i<num_base_classes; ++i)
- {
- delete base_classes[i];
- base_classes[i] = nullptr;
- }
-}
+ClangASTContext::CreateBaseClassSpecifier(lldb::opaque_compiler_type_t type,
+ AccessType access, bool is_virtual,
+ bool base_of_class) {
+ if (type)
+ return new clang::CXXBaseSpecifier(
+ clang::SourceRange(), is_virtual, base_of_class,
+ ClangASTContext::ConvertAccessTypeToAccessSpecifier(access),
+ getASTContext()->getTrivialTypeSourceInfo(GetQualType(type)),
+ clang::SourceLocation());
+ return nullptr;
+}
+
+void ClangASTContext::DeleteBaseClassSpecifiers(
+ clang::CXXBaseSpecifier **base_classes, unsigned num_base_classes) {
+ for (unsigned i = 0; i < num_base_classes; ++i) {
+ delete base_classes[i];
+ base_classes[i] = nullptr;
+ }
+}
+
+bool ClangASTContext::SetBaseClassesForClassType(
+ lldb::opaque_compiler_type_t type,
+ clang::CXXBaseSpecifier const *const *base_classes,
+ unsigned num_base_classes) {
+ if (type) {
+ clang::CXXRecordDecl *cxx_record_decl = GetAsCXXRecordDecl(type);
+ if (cxx_record_decl) {
+ cxx_record_decl->setBases(base_classes, num_base_classes);
+ return true;
+ }
+ }
+ return false;
+}
+
+bool ClangASTContext::SetObjCSuperClass(
+ const CompilerType &type, const CompilerType &superclass_clang_type) {
+ ClangASTContext *ast =
+ llvm::dyn_cast_or_null<ClangASTContext>(type.GetTypeSystem());
+ if (!ast)
+ return false;
+ clang::ASTContext *clang_ast = ast->getASTContext();
+
+ if (type && superclass_clang_type.IsValid() &&
+ superclass_clang_type.GetTypeSystem() == type.GetTypeSystem()) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ GetAsObjCInterfaceDecl(type);
+ clang::ObjCInterfaceDecl *super_interface_decl =
+ GetAsObjCInterfaceDecl(superclass_clang_type);
+ if (class_interface_decl && super_interface_decl) {
+ class_interface_decl->setSuperClass(clang_ast->getTrivialTypeSourceInfo(
+ clang_ast->getObjCInterfaceType(super_interface_decl)));
+ return true;
+ }
+ }
+ return false;
+}
+
+bool ClangASTContext::AddObjCClassProperty(
+ const CompilerType &type, const char *property_name,
+ const CompilerType &property_clang_type, clang::ObjCIvarDecl *ivar_decl,
+ const char *property_setter_name, const char *property_getter_name,
+ uint32_t property_attributes, ClangASTMetadata *metadata) {
+ if (!type || !property_clang_type.IsValid() || property_name == nullptr ||
+ property_name[0] == '\0')
+ return false;
+ ClangASTContext *ast = llvm::dyn_cast<ClangASTContext>(type.GetTypeSystem());
+ if (!ast)
+ return false;
+ clang::ASTContext *clang_ast = ast->getASTContext();
+
+ clang::ObjCInterfaceDecl *class_interface_decl = GetAsObjCInterfaceDecl(type);
+
+ if (class_interface_decl) {
+ CompilerType property_clang_type_to_access;
+
+ if (property_clang_type.IsValid())
+ property_clang_type_to_access = property_clang_type;
+ else if (ivar_decl)
+ property_clang_type_to_access =
+ CompilerType(clang_ast, ivar_decl->getType());
+
+ if (class_interface_decl && property_clang_type_to_access.IsValid()) {
+ clang::TypeSourceInfo *prop_type_source;
+ if (ivar_decl)
+ prop_type_source =
+ clang_ast->getTrivialTypeSourceInfo(ivar_decl->getType());
+ else
+ prop_type_source = clang_ast->getTrivialTypeSourceInfo(
+ ClangUtil::GetQualType(property_clang_type));
+
+ clang::ObjCPropertyDecl *property_decl = clang::ObjCPropertyDecl::Create(
+ *clang_ast, class_interface_decl,
+ clang::SourceLocation(), // Source Location
+ &clang_ast->Idents.get(property_name),
+ clang::SourceLocation(), // Source Location for AT
+ clang::SourceLocation(), // Source location for (
+ ivar_decl ? ivar_decl->getType()
+ : ClangUtil::GetQualType(property_clang_type),
+ prop_type_source);
+
+ if (property_decl) {
+ if (metadata)
+ ClangASTContext::SetMetadata(clang_ast, property_decl, *metadata);
+
+ class_interface_decl->addDecl(property_decl);
+
+ clang::Selector setter_sel, getter_sel;
+
+ if (property_setter_name != nullptr) {
+ std::string property_setter_no_colon(
+ property_setter_name, strlen(property_setter_name) - 1);
+ clang::IdentifierInfo *setter_ident =
+ &clang_ast->Idents.get(property_setter_no_colon.c_str());
+ setter_sel = clang_ast->Selectors.getSelector(1, &setter_ident);
+ } else if (!(property_attributes & DW_APPLE_PROPERTY_readonly)) {
+ std::string setter_sel_string("set");
+ setter_sel_string.push_back(::toupper(property_name[0]));
+ setter_sel_string.append(&property_name[1]);
+ clang::IdentifierInfo *setter_ident =
+ &clang_ast->Idents.get(setter_sel_string.c_str());
+ setter_sel = clang_ast->Selectors.getSelector(1, &setter_ident);
+ }
+ property_decl->setSetterName(setter_sel);
+ property_decl->setPropertyAttributes(
+ clang::ObjCPropertyDecl::OBJC_PR_setter);
+
+ if (property_getter_name != nullptr) {
+ clang::IdentifierInfo *getter_ident =
+ &clang_ast->Idents.get(property_getter_name);
+ getter_sel = clang_ast->Selectors.getSelector(0, &getter_ident);
+ } else {
+ clang::IdentifierInfo *getter_ident =
+ &clang_ast->Idents.get(property_name);
+ getter_sel = clang_ast->Selectors.getSelector(0, &getter_ident);
+ }
+ property_decl->setGetterName(getter_sel);
+ property_decl->setPropertyAttributes(
+ clang::ObjCPropertyDecl::OBJC_PR_getter);
+
+ if (ivar_decl)
+ property_decl->setPropertyIvarDecl(ivar_decl);
+
+ if (property_attributes & DW_APPLE_PROPERTY_readonly)
+ property_decl->setPropertyAttributes(
+ clang::ObjCPropertyDecl::OBJC_PR_readonly);
+ if (property_attributes & DW_APPLE_PROPERTY_readwrite)
+ property_decl->setPropertyAttributes(
+ clang::ObjCPropertyDecl::OBJC_PR_readwrite);
+ if (property_attributes & DW_APPLE_PROPERTY_assign)
+ property_decl->setPropertyAttributes(
+ clang::ObjCPropertyDecl::OBJC_PR_assign);
+ if (property_attributes & DW_APPLE_PROPERTY_retain)
+ property_decl->setPropertyAttributes(
+ clang::ObjCPropertyDecl::OBJC_PR_retain);
+ if (property_attributes & DW_APPLE_PROPERTY_copy)
+ property_decl->setPropertyAttributes(
+ clang::ObjCPropertyDecl::OBJC_PR_copy);
+ if (property_attributes & DW_APPLE_PROPERTY_nonatomic)
+ property_decl->setPropertyAttributes(
+ clang::ObjCPropertyDecl::OBJC_PR_nonatomic);
+ if (property_attributes & clang::ObjCPropertyDecl::OBJC_PR_nullability)
+ property_decl->setPropertyAttributes(
+ clang::ObjCPropertyDecl::OBJC_PR_nullability);
+ if (property_attributes &
+ clang::ObjCPropertyDecl::OBJC_PR_null_resettable)
+ property_decl->setPropertyAttributes(
+ clang::ObjCPropertyDecl::OBJC_PR_null_resettable);
+ if (property_attributes & clang::ObjCPropertyDecl::OBJC_PR_class)
+ property_decl->setPropertyAttributes(
+ clang::ObjCPropertyDecl::OBJC_PR_class);
+
+ const bool isInstance =
+ (property_attributes & clang::ObjCPropertyDecl::OBJC_PR_class) == 0;
+
+ if (!getter_sel.isNull() &&
+ !(isInstance
+ ? class_interface_decl->lookupInstanceMethod(getter_sel)
+ : class_interface_decl->lookupClassMethod(getter_sel))) {
+ const bool isVariadic = false;
+ const bool isSynthesized = false;
+ const bool isImplicitlyDeclared = true;
+ const bool isDefined = false;
+ const clang::ObjCMethodDecl::ImplementationControl impControl =
+ clang::ObjCMethodDecl::None;
+ const bool HasRelatedResultType = false;
+
+ clang::ObjCMethodDecl *getter = clang::ObjCMethodDecl::Create(
+ *clang_ast, clang::SourceLocation(), clang::SourceLocation(),
+ getter_sel, ClangUtil::GetQualType(property_clang_type_to_access),
+ nullptr, class_interface_decl, isInstance, isVariadic,
+ isSynthesized, isImplicitlyDeclared, isDefined, impControl,
+ HasRelatedResultType);
+
+ if (getter && metadata)
+ ClangASTContext::SetMetadata(clang_ast, getter, *metadata);
+
+ if (getter) {
+ getter->setMethodParams(*clang_ast,
+ llvm::ArrayRef<clang::ParmVarDecl *>(),
+ llvm::ArrayRef<clang::SourceLocation>());
+
+ class_interface_decl->addDecl(getter);
+ }
+ }
-bool
-ClangASTContext::SetBaseClassesForClassType (lldb::opaque_compiler_type_t type, clang::CXXBaseSpecifier const * const *base_classes,
- unsigned num_base_classes)
-{
- if (type)
- {
- clang::CXXRecordDecl *cxx_record_decl = GetAsCXXRecordDecl(type);
- if (cxx_record_decl)
- {
- cxx_record_decl->setBases(base_classes, num_base_classes);
- return true;
+ if (!setter_sel.isNull() &&
+ !(isInstance
+ ? class_interface_decl->lookupInstanceMethod(setter_sel)
+ : class_interface_decl->lookupClassMethod(setter_sel))) {
+ clang::QualType result_type = clang_ast->VoidTy;
+ const bool isVariadic = false;
+ const bool isSynthesized = false;
+ const bool isImplicitlyDeclared = true;
+ const bool isDefined = false;
+ const clang::ObjCMethodDecl::ImplementationControl impControl =
+ clang::ObjCMethodDecl::None;
+ const bool HasRelatedResultType = false;
+
+ clang::ObjCMethodDecl *setter = clang::ObjCMethodDecl::Create(
+ *clang_ast, clang::SourceLocation(), clang::SourceLocation(),
+ setter_sel, result_type, nullptr, class_interface_decl,
+ isInstance, isVariadic, isSynthesized, isImplicitlyDeclared,
+ isDefined, impControl, HasRelatedResultType);
+
+ if (setter && metadata)
+ ClangASTContext::SetMetadata(clang_ast, setter, *metadata);
+
+ llvm::SmallVector<clang::ParmVarDecl *, 1> params;
+
+ params.push_back(clang::ParmVarDecl::Create(
+ *clang_ast, setter, clang::SourceLocation(),
+ clang::SourceLocation(),
+ nullptr, // anonymous
+ ClangUtil::GetQualType(property_clang_type_to_access), nullptr,
+ clang::SC_Auto, nullptr));
+
+ if (setter) {
+ setter->setMethodParams(
+ *clang_ast, llvm::ArrayRef<clang::ParmVarDecl *>(params),
+ llvm::ArrayRef<clang::SourceLocation>());
+
+ class_interface_decl->addDecl(setter);
+ }
}
+
+ return true;
+ }
}
- return false;
+ }
+ return false;
}
-bool
-ClangASTContext::SetObjCSuperClass (const CompilerType& type, const CompilerType &superclass_clang_type)
-{
- ClangASTContext *ast = llvm::dyn_cast_or_null<ClangASTContext>(type.GetTypeSystem());
- if (!ast)
- return false;
- clang::ASTContext* clang_ast = ast->getASTContext();
-
- if (type && superclass_clang_type.IsValid() && superclass_clang_type.GetTypeSystem() == type.GetTypeSystem())
- {
- clang::ObjCInterfaceDecl *class_interface_decl = GetAsObjCInterfaceDecl (type);
- clang::ObjCInterfaceDecl *super_interface_decl = GetAsObjCInterfaceDecl (superclass_clang_type);
- if (class_interface_decl && super_interface_decl)
- {
- class_interface_decl->setSuperClass(clang_ast->getTrivialTypeSourceInfo(clang_ast->getObjCInterfaceType(super_interface_decl)));
- return true;
- }
- }
- return false;
+bool ClangASTContext::IsObjCClassTypeAndHasIVars(const CompilerType &type,
+ bool check_superclass) {
+ clang::ObjCInterfaceDecl *class_interface_decl = GetAsObjCInterfaceDecl(type);
+ if (class_interface_decl)
+ return ObjCDeclHasIVars(class_interface_decl, check_superclass);
+ return false;
}
-bool
-ClangASTContext::AddObjCClassProperty (const CompilerType& type,
- const char *property_name,
- const CompilerType &property_clang_type,
- clang::ObjCIvarDecl *ivar_decl,
- const char *property_setter_name,
- const char *property_getter_name,
- uint32_t property_attributes,
- ClangASTMetadata *metadata)
-{
- if (!type || !property_clang_type.IsValid() || property_name == nullptr || property_name[0] == '\0')
- return false;
- ClangASTContext *ast = llvm::dyn_cast<ClangASTContext>(type.GetTypeSystem());
- if (!ast)
- return false;
- clang::ASTContext* clang_ast = ast->getASTContext();
-
- clang::ObjCInterfaceDecl *class_interface_decl = GetAsObjCInterfaceDecl (type);
-
- if (class_interface_decl)
- {
- CompilerType property_clang_type_to_access;
-
- if (property_clang_type.IsValid())
- property_clang_type_to_access = property_clang_type;
- else if (ivar_decl)
- property_clang_type_to_access = CompilerType (clang_ast, ivar_decl->getType());
-
- if (class_interface_decl && property_clang_type_to_access.IsValid())
- {
- clang::TypeSourceInfo *prop_type_source;
- if (ivar_decl)
- prop_type_source = clang_ast->getTrivialTypeSourceInfo (ivar_decl->getType());
- else
- prop_type_source = clang_ast->getTrivialTypeSourceInfo(ClangUtil::GetQualType(property_clang_type));
-
- clang::ObjCPropertyDecl *property_decl = clang::ObjCPropertyDecl::Create(
- *clang_ast, class_interface_decl,
- clang::SourceLocation(), // Source Location
- &clang_ast->Idents.get(property_name),
- clang::SourceLocation(), // Source Location for AT
- clang::SourceLocation(), // Source location for (
- ivar_decl ? ivar_decl->getType() : ClangUtil::GetQualType(property_clang_type), prop_type_source);
-
- if (property_decl)
- {
- if (metadata)
- ClangASTContext::SetMetadata(clang_ast, property_decl, *metadata);
-
- class_interface_decl->addDecl (property_decl);
-
- clang::Selector setter_sel, getter_sel;
-
- if (property_setter_name != nullptr)
- {
- std::string property_setter_no_colon(property_setter_name, strlen(property_setter_name) - 1);
- clang::IdentifierInfo *setter_ident = &clang_ast->Idents.get(property_setter_no_colon.c_str());
- setter_sel = clang_ast->Selectors.getSelector(1, &setter_ident);
- }
- else if (!(property_attributes & DW_APPLE_PROPERTY_readonly))
- {
- std::string setter_sel_string("set");
- setter_sel_string.push_back(::toupper(property_name[0]));
- setter_sel_string.append(&property_name[1]);
- clang::IdentifierInfo *setter_ident = &clang_ast->Idents.get(setter_sel_string.c_str());
- setter_sel = clang_ast->Selectors.getSelector(1, &setter_ident);
- }
- property_decl->setSetterName(setter_sel);
- property_decl->setPropertyAttributes (clang::ObjCPropertyDecl::OBJC_PR_setter);
-
- if (property_getter_name != nullptr)
- {
- clang::IdentifierInfo *getter_ident = &clang_ast->Idents.get(property_getter_name);
- getter_sel = clang_ast->Selectors.getSelector(0, &getter_ident);
- }
- else
- {
- clang::IdentifierInfo *getter_ident = &clang_ast->Idents.get(property_name);
- getter_sel = clang_ast->Selectors.getSelector(0, &getter_ident);
- }
- property_decl->setGetterName(getter_sel);
- property_decl->setPropertyAttributes (clang::ObjCPropertyDecl::OBJC_PR_getter);
-
- if (ivar_decl)
- property_decl->setPropertyIvarDecl (ivar_decl);
-
- if (property_attributes & DW_APPLE_PROPERTY_readonly)
- property_decl->setPropertyAttributes (clang::ObjCPropertyDecl::OBJC_PR_readonly);
- if (property_attributes & DW_APPLE_PROPERTY_readwrite)
- property_decl->setPropertyAttributes (clang::ObjCPropertyDecl::OBJC_PR_readwrite);
- if (property_attributes & DW_APPLE_PROPERTY_assign)
- property_decl->setPropertyAttributes (clang::ObjCPropertyDecl::OBJC_PR_assign);
- if (property_attributes & DW_APPLE_PROPERTY_retain)
- property_decl->setPropertyAttributes (clang::ObjCPropertyDecl::OBJC_PR_retain);
- if (property_attributes & DW_APPLE_PROPERTY_copy)
- property_decl->setPropertyAttributes (clang::ObjCPropertyDecl::OBJC_PR_copy);
- if (property_attributes & DW_APPLE_PROPERTY_nonatomic)
- property_decl->setPropertyAttributes (clang::ObjCPropertyDecl::OBJC_PR_nonatomic);
- if (property_attributes & clang::ObjCPropertyDecl::OBJC_PR_nullability)
- property_decl->setPropertyAttributes(clang::ObjCPropertyDecl::OBJC_PR_nullability);
- if (property_attributes & clang::ObjCPropertyDecl::OBJC_PR_null_resettable)
- property_decl->setPropertyAttributes(clang::ObjCPropertyDecl::OBJC_PR_null_resettable);
- if (property_attributes & clang::ObjCPropertyDecl::OBJC_PR_class)
- property_decl->setPropertyAttributes(clang::ObjCPropertyDecl::OBJC_PR_class);
-
- const bool isInstance = (property_attributes & clang::ObjCPropertyDecl::OBJC_PR_class) == 0;
-
- if (!getter_sel.isNull() &&
- !(isInstance ? class_interface_decl->lookupInstanceMethod(getter_sel)
- : class_interface_decl->lookupClassMethod(getter_sel)))
- {
- const bool isVariadic = false;
- const bool isSynthesized = false;
- const bool isImplicitlyDeclared = true;
- const bool isDefined = false;
- const clang::ObjCMethodDecl::ImplementationControl impControl = clang::ObjCMethodDecl::None;
- const bool HasRelatedResultType = false;
-
- clang::ObjCMethodDecl *getter = clang::ObjCMethodDecl::Create(
- *clang_ast, clang::SourceLocation(), clang::SourceLocation(), getter_sel,
- ClangUtil::GetQualType(property_clang_type_to_access), nullptr, class_interface_decl,
- isInstance, isVariadic, isSynthesized, isImplicitlyDeclared, isDefined, impControl,
- HasRelatedResultType);
-
- if (getter && metadata)
- ClangASTContext::SetMetadata(clang_ast, getter, *metadata);
-
- if (getter)
- {
- getter->setMethodParams(*clang_ast, llvm::ArrayRef<clang::ParmVarDecl*>(), llvm::ArrayRef<clang::SourceLocation>());
-
- class_interface_decl->addDecl(getter);
- }
- }
+clang::ObjCMethodDecl *ClangASTContext::AddMethodToObjCObjectType(
+ const CompilerType &type,
+ const char *name, // the full symbol name as seen in the symbol table
+ // (lldb::opaque_compiler_type_t type, "-[NString
+ // stringWithCString:]")
+ const CompilerType &method_clang_type, lldb::AccessType access,
+ bool is_artificial, bool is_variadic) {
+ if (!type || !method_clang_type.IsValid())
+ return nullptr;
- if (!setter_sel.isNull() &&
- !(isInstance ? class_interface_decl->lookupInstanceMethod(setter_sel)
- : class_interface_decl->lookupClassMethod(setter_sel)))
- {
- clang::QualType result_type = clang_ast->VoidTy;
- const bool isVariadic = false;
- const bool isSynthesized = false;
- const bool isImplicitlyDeclared = true;
- const bool isDefined = false;
- const clang::ObjCMethodDecl::ImplementationControl impControl = clang::ObjCMethodDecl::None;
- const bool HasRelatedResultType = false;
-
- clang::ObjCMethodDecl *setter = clang::ObjCMethodDecl::Create (*clang_ast,
- clang::SourceLocation(),
- clang::SourceLocation(),
- setter_sel,
- result_type,
- nullptr,
- class_interface_decl,
- isInstance,
- isVariadic,
- isSynthesized,
- isImplicitlyDeclared,
- isDefined,
- impControl,
- HasRelatedResultType);
-
- if (setter && metadata)
- ClangASTContext::SetMetadata(clang_ast, setter, *metadata);
-
- llvm::SmallVector<clang::ParmVarDecl *, 1> params;
-
- params.push_back(clang::ParmVarDecl::Create(
- *clang_ast, setter, clang::SourceLocation(), clang::SourceLocation(),
- nullptr, // anonymous
- ClangUtil::GetQualType(property_clang_type_to_access), nullptr, clang::SC_Auto, nullptr));
-
- if (setter)
- {
- setter->setMethodParams(*clang_ast, llvm::ArrayRef<clang::ParmVarDecl*>(params), llvm::ArrayRef<clang::SourceLocation>());
-
- class_interface_decl->addDecl(setter);
- }
- }
-
- return true;
- }
- }
- }
- return false;
-}
+ clang::ObjCInterfaceDecl *class_interface_decl = GetAsObjCInterfaceDecl(type);
-bool
-ClangASTContext::IsObjCClassTypeAndHasIVars (const CompilerType& type, bool check_superclass)
-{
- clang::ObjCInterfaceDecl *class_interface_decl = GetAsObjCInterfaceDecl (type);
- if (class_interface_decl)
- return ObjCDeclHasIVars (class_interface_decl, check_superclass);
- return false;
-}
+ if (class_interface_decl == nullptr)
+ return nullptr;
+ ClangASTContext *lldb_ast =
+ llvm::dyn_cast<ClangASTContext>(type.GetTypeSystem());
+ if (lldb_ast == nullptr)
+ return nullptr;
+ clang::ASTContext *ast = lldb_ast->getASTContext();
+ const char *selector_start = ::strchr(name, ' ');
+ if (selector_start == nullptr)
+ return nullptr;
-clang::ObjCMethodDecl *
-ClangASTContext::AddMethodToObjCObjectType (const CompilerType& type,
- const char *name, // the full symbol name as seen in the symbol table (lldb::opaque_compiler_type_t type, "-[NString stringWithCString:]")
- const CompilerType &method_clang_type,
- lldb::AccessType access,
- bool is_artificial,
- bool is_variadic)
-{
- if (!type || !method_clang_type.IsValid())
- return nullptr;
-
- clang::ObjCInterfaceDecl *class_interface_decl = GetAsObjCInterfaceDecl(type);
-
- if (class_interface_decl == nullptr)
- return nullptr;
- ClangASTContext *lldb_ast = llvm::dyn_cast<ClangASTContext>(type.GetTypeSystem());
- if (lldb_ast == nullptr)
- return nullptr;
- clang::ASTContext *ast = lldb_ast->getASTContext();
-
- const char *selector_start = ::strchr (name, ' ');
- if (selector_start == nullptr)
- return nullptr;
-
- selector_start++;
- llvm::SmallVector<clang::IdentifierInfo *, 12> selector_idents;
-
- size_t len = 0;
- const char *start;
- //printf ("name = '%s'\n", name);
-
- unsigned num_selectors_with_args = 0;
- for (start = selector_start;
- start && *start != '\0' && *start != ']';
- start += len)
- {
- len = ::strcspn(start, ":]");
- bool has_arg = (start[len] == ':');
- if (has_arg)
- ++num_selectors_with_args;
- selector_idents.push_back (&ast->Idents.get (llvm::StringRef (start, len)));
- if (has_arg)
- len += 1;
- }
-
-
- if (selector_idents.size() == 0)
- return nullptr;
-
- clang::Selector method_selector = ast->Selectors.getSelector (num_selectors_with_args ? selector_idents.size() : 0,
- selector_idents.data());
-
- clang::QualType method_qual_type(ClangUtil::GetQualType(method_clang_type));
-
- // Populate the method decl with parameter decls
- const clang::Type *method_type(method_qual_type.getTypePtr());
-
- if (method_type == nullptr)
- return nullptr;
-
- const clang::FunctionProtoType *method_function_prototype (llvm::dyn_cast<clang::FunctionProtoType>(method_type));
-
- if (!method_function_prototype)
- return nullptr;
-
-
- bool is_synthesized = false;
- bool is_defined = false;
- clang::ObjCMethodDecl::ImplementationControl imp_control = clang::ObjCMethodDecl::None;
-
- const unsigned num_args = method_function_prototype->getNumParams();
-
- if (num_args != num_selectors_with_args)
- return nullptr; // some debug information is corrupt. We are not going to deal with it.
-
- clang::ObjCMethodDecl *objc_method_decl = clang::ObjCMethodDecl::Create(
- *ast,
- clang::SourceLocation(), // beginLoc,
- clang::SourceLocation(), // endLoc,
- method_selector, method_function_prototype->getReturnType(),
- nullptr, // TypeSourceInfo *ResultTInfo,
- ClangASTContext::GetASTContext(ast)->GetDeclContextForType(ClangUtil::GetQualType(type)), name[0] == '-',
- is_variadic, is_synthesized,
- true, // is_implicitly_declared; we force this to true because we don't have source locations
- is_defined, imp_control, false /*has_related_result_type*/);
-
- if (objc_method_decl == nullptr)
- return nullptr;
-
- if (num_args > 0)
- {
- llvm::SmallVector<clang::ParmVarDecl *, 12> params;
-
- for (unsigned param_index = 0; param_index < num_args; ++param_index)
- {
- params.push_back (clang::ParmVarDecl::Create (*ast,
- objc_method_decl,
- clang::SourceLocation(),
- clang::SourceLocation(),
- nullptr, // anonymous
- method_function_prototype->getParamType(param_index),
- nullptr,
- clang::SC_Auto,
- nullptr));
- }
-
- objc_method_decl->setMethodParams(*ast, llvm::ArrayRef<clang::ParmVarDecl*>(params), llvm::ArrayRef<clang::SourceLocation>());
+ selector_start++;
+ llvm::SmallVector<clang::IdentifierInfo *, 12> selector_idents;
+
+ size_t len = 0;
+ const char *start;
+ // printf ("name = '%s'\n", name);
+
+ unsigned num_selectors_with_args = 0;
+ for (start = selector_start; start && *start != '\0' && *start != ']';
+ start += len) {
+ len = ::strcspn(start, ":]");
+ bool has_arg = (start[len] == ':');
+ if (has_arg)
+ ++num_selectors_with_args;
+ selector_idents.push_back(&ast->Idents.get(llvm::StringRef(start, len)));
+ if (has_arg)
+ len += 1;
+ }
+
+ if (selector_idents.size() == 0)
+ return nullptr;
+
+ clang::Selector method_selector = ast->Selectors.getSelector(
+ num_selectors_with_args ? selector_idents.size() : 0,
+ selector_idents.data());
+
+ clang::QualType method_qual_type(ClangUtil::GetQualType(method_clang_type));
+
+ // Populate the method decl with parameter decls
+ const clang::Type *method_type(method_qual_type.getTypePtr());
+
+ if (method_type == nullptr)
+ return nullptr;
+
+ const clang::FunctionProtoType *method_function_prototype(
+ llvm::dyn_cast<clang::FunctionProtoType>(method_type));
+
+ if (!method_function_prototype)
+ return nullptr;
+
+ bool is_synthesized = false;
+ bool is_defined = false;
+ clang::ObjCMethodDecl::ImplementationControl imp_control =
+ clang::ObjCMethodDecl::None;
+
+ const unsigned num_args = method_function_prototype->getNumParams();
+
+ if (num_args != num_selectors_with_args)
+ return nullptr; // some debug information is corrupt. We are not going to
+ // deal with it.
+
+ clang::ObjCMethodDecl *objc_method_decl = clang::ObjCMethodDecl::Create(
+ *ast,
+ clang::SourceLocation(), // beginLoc,
+ clang::SourceLocation(), // endLoc,
+ method_selector, method_function_prototype->getReturnType(),
+ nullptr, // TypeSourceInfo *ResultTInfo,
+ ClangASTContext::GetASTContext(ast)->GetDeclContextForType(
+ ClangUtil::GetQualType(type)),
+ name[0] == '-', is_variadic, is_synthesized,
+ true, // is_implicitly_declared; we force this to true because we don't
+ // have source locations
+ is_defined, imp_control, false /*has_related_result_type*/);
+
+ if (objc_method_decl == nullptr)
+ return nullptr;
+
+ if (num_args > 0) {
+ llvm::SmallVector<clang::ParmVarDecl *, 12> params;
+
+ for (unsigned param_index = 0; param_index < num_args; ++param_index) {
+ params.push_back(clang::ParmVarDecl::Create(
+ *ast, objc_method_decl, clang::SourceLocation(),
+ clang::SourceLocation(),
+ nullptr, // anonymous
+ method_function_prototype->getParamType(param_index), nullptr,
+ clang::SC_Auto, nullptr));
}
-
- class_interface_decl->addDecl (objc_method_decl);
-
+
+ objc_method_decl->setMethodParams(
+ *ast, llvm::ArrayRef<clang::ParmVarDecl *>(params),
+ llvm::ArrayRef<clang::SourceLocation>());
+ }
+
+ class_interface_decl->addDecl(objc_method_decl);
+
#ifdef LLDB_CONFIGURATION_DEBUG
- VerifyDecl(objc_method_decl);
+ VerifyDecl(objc_method_decl);
#endif
-
- return objc_method_decl;
+
+ return objc_method_decl;
}
-bool
-ClangASTContext::GetHasExternalStorage (const CompilerType &type)
-{
- if (ClangUtil::IsClangType(type))
- return false;
+bool ClangASTContext::GetHasExternalStorage(const CompilerType &type) {
+ if (ClangUtil::IsClangType(type))
+ return false;
- clang::QualType qual_type(ClangUtil::GetCanonicalQualType(type));
+ clang::QualType qual_type(ClangUtil::GetCanonicalQualType(type));
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Record:
- {
- clang::CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
- if (cxx_record_decl)
- return cxx_record_decl->hasExternalLexicalStorage () || cxx_record_decl->hasExternalVisibleStorage();
- }
- break;
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Record: {
+ clang::CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
+ if (cxx_record_decl)
+ return cxx_record_decl->hasExternalLexicalStorage() ||
+ cxx_record_decl->hasExternalVisibleStorage();
+ } break;
- case clang::Type::Enum:
- {
- clang::EnumDecl *enum_decl = llvm::cast<clang::EnumType>(qual_type)->getDecl();
- if (enum_decl)
- return enum_decl->hasExternalLexicalStorage () || enum_decl->hasExternalVisibleStorage();
- }
- break;
+ case clang::Type::Enum: {
+ clang::EnumDecl *enum_decl =
+ llvm::cast<clang::EnumType>(qual_type)->getDecl();
+ if (enum_decl)
+ return enum_decl->hasExternalLexicalStorage() ||
+ enum_decl->hasExternalVisibleStorage();
+ } break;
- case clang::Type::ObjCObject:
- case clang::Type::ObjCInterface:
- {
- const clang::ObjCObjectType *objc_class_type = llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
- assert (objc_class_type);
- if (objc_class_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
-
- if (class_interface_decl)
- return class_interface_decl->hasExternalLexicalStorage () || class_interface_decl->hasExternalVisibleStorage ();
- }
- }
- break;
+ case clang::Type::ObjCObject:
+ case clang::Type::ObjCInterface: {
+ const clang::ObjCObjectType *objc_class_type =
+ llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
+ assert(objc_class_type);
+ if (objc_class_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterface();
+
+ if (class_interface_decl)
+ return class_interface_decl->hasExternalLexicalStorage() ||
+ class_interface_decl->hasExternalVisibleStorage();
+ }
+ } break;
+
+ case clang::Type::Typedef:
+ return GetHasExternalStorage(CompilerType(
+ type.GetTypeSystem(), llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr()));
+
+ case clang::Type::Auto:
+ return GetHasExternalStorage(CompilerType(
+ type.GetTypeSystem(), llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr()));
+
+ case clang::Type::Elaborated:
+ return GetHasExternalStorage(CompilerType(
+ type.GetTypeSystem(), llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr()));
+
+ case clang::Type::Paren:
+ return GetHasExternalStorage(CompilerType(
+ type.GetTypeSystem(),
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr()));
+
+ default:
+ break;
+ }
+ return false;
+}
+
+bool ClangASTContext::SetHasExternalStorage(lldb::opaque_compiler_type_t type,
+ bool has_extern) {
+ if (!type)
+ return false;
- case clang::Type::Typedef:
- return GetHasExternalStorage (CompilerType(type.GetTypeSystem(), llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr()));
+ clang::QualType qual_type(GetCanonicalQualType(type));
- case clang::Type::Auto:
- return GetHasExternalStorage (CompilerType(type.GetTypeSystem(), llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr()));
-
- case clang::Type::Elaborated:
- return GetHasExternalStorage (CompilerType(type.GetTypeSystem(), llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr()));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Record: {
+ clang::CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
+ if (cxx_record_decl) {
+ cxx_record_decl->setHasExternalLexicalStorage(has_extern);
+ cxx_record_decl->setHasExternalVisibleStorage(has_extern);
+ return true;
+ }
+ } break;
- case clang::Type::Paren:
- return GetHasExternalStorage (CompilerType(type.GetTypeSystem(), llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr()));
+ case clang::Type::Enum: {
+ clang::EnumDecl *enum_decl =
+ llvm::cast<clang::EnumType>(qual_type)->getDecl();
+ if (enum_decl) {
+ enum_decl->setHasExternalLexicalStorage(has_extern);
+ enum_decl->setHasExternalVisibleStorage(has_extern);
+ return true;
+ }
+ } break;
- default:
- break;
+ case clang::Type::ObjCObject:
+ case clang::Type::ObjCInterface: {
+ const clang::ObjCObjectType *objc_class_type =
+ llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
+ assert(objc_class_type);
+ if (objc_class_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterface();
+
+ if (class_interface_decl) {
+ class_interface_decl->setHasExternalLexicalStorage(has_extern);
+ class_interface_decl->setHasExternalVisibleStorage(has_extern);
+ return true;
+ }
}
- return false;
-}
+ } break;
+ case clang::Type::Typedef:
+ return SetHasExternalStorage(llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType()
+ .getAsOpaquePtr(),
+ has_extern);
-bool
-ClangASTContext::SetHasExternalStorage (lldb::opaque_compiler_type_t type, bool has_extern)
-{
- if (!type)
- return false;
-
- clang::QualType qual_type (GetCanonicalQualType(type));
-
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Record:
- {
- clang::CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
- if (cxx_record_decl)
- {
- cxx_record_decl->setHasExternalLexicalStorage (has_extern);
- cxx_record_decl->setHasExternalVisibleStorage (has_extern);
- return true;
- }
- }
- break;
-
- case clang::Type::Enum:
- {
- clang::EnumDecl *enum_decl = llvm::cast<clang::EnumType>(qual_type)->getDecl();
- if (enum_decl)
- {
- enum_decl->setHasExternalLexicalStorage (has_extern);
- enum_decl->setHasExternalVisibleStorage (has_extern);
- return true;
- }
- }
- break;
-
- case clang::Type::ObjCObject:
- case clang::Type::ObjCInterface:
- {
- const clang::ObjCObjectType *objc_class_type = llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
- assert (objc_class_type);
- if (objc_class_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
-
- if (class_interface_decl)
- {
- class_interface_decl->setHasExternalLexicalStorage (has_extern);
- class_interface_decl->setHasExternalVisibleStorage (has_extern);
- return true;
- }
- }
- }
- break;
-
- case clang::Type::Typedef:
- return SetHasExternalStorage(llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType().getAsOpaquePtr(), has_extern);
-
- case clang::Type::Auto:
- return SetHasExternalStorage (llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr(), has_extern);
-
- case clang::Type::Elaborated:
- return SetHasExternalStorage (llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr(), has_extern);
-
- case clang::Type::Paren:
- return SetHasExternalStorage (llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(), has_extern);
-
- default:
- break;
- }
- return false;
-}
+ case clang::Type::Auto:
+ return SetHasExternalStorage(llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr(),
+ has_extern);
+
+ case clang::Type::Elaborated:
+ return SetHasExternalStorage(llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr(),
+ has_extern);
+
+ case clang::Type::Paren:
+ return SetHasExternalStorage(
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(),
+ has_extern);
+ default:
+ break;
+ }
+ return false;
+}
#pragma mark TagDecl
-bool
-ClangASTContext::StartTagDeclarationDefinition (const CompilerType &type)
-{
- clang::QualType qual_type(ClangUtil::GetQualType(type));
- if (!qual_type.isNull())
- {
- const clang::TagType *tag_type = qual_type->getAs<clang::TagType>();
- if (tag_type)
- {
- clang::TagDecl *tag_decl = tag_type->getDecl();
- if (tag_decl)
- {
- tag_decl->startDefinition();
- return true;
- }
- }
-
- const clang::ObjCObjectType *object_type = qual_type->getAs<clang::ObjCObjectType>();
- if (object_type)
- {
- clang::ObjCInterfaceDecl *interface_decl = object_type->getInterface();
- if (interface_decl)
- {
- interface_decl->startDefinition();
- return true;
- }
- }
+bool ClangASTContext::StartTagDeclarationDefinition(const CompilerType &type) {
+ clang::QualType qual_type(ClangUtil::GetQualType(type));
+ if (!qual_type.isNull()) {
+ const clang::TagType *tag_type = qual_type->getAs<clang::TagType>();
+ if (tag_type) {
+ clang::TagDecl *tag_decl = tag_type->getDecl();
+ if (tag_decl) {
+ tag_decl->startDefinition();
+ return true;
+ }
}
- return false;
-}
-bool
-ClangASTContext::CompleteTagDeclarationDefinition (const CompilerType& type)
-{
- clang::QualType qual_type(ClangUtil::GetQualType(type));
- if (!qual_type.isNull())
- {
- // Make sure we use the same methodology as ClangASTContext::StartTagDeclarationDefinition()
- // as to how we start/end the definition. Previously we were calling
- const clang::TagType *tag_type = qual_type->getAs<clang::TagType>();
- if (tag_type)
- {
- clang::TagDecl *tag_decl = tag_type->getDecl();
- if (tag_decl)
- {
- clang::CXXRecordDecl *cxx_record_decl = llvm::dyn_cast_or_null<clang::CXXRecordDecl>(tag_decl);
-
- if (cxx_record_decl)
- {
- if (!cxx_record_decl->isCompleteDefinition())
- cxx_record_decl->completeDefinition();
- cxx_record_decl->setHasLoadedFieldsFromExternalStorage(true);
- cxx_record_decl->setHasExternalLexicalStorage (false);
- cxx_record_decl->setHasExternalVisibleStorage (false);
- return true;
- }
- }
+ const clang::ObjCObjectType *object_type =
+ qual_type->getAs<clang::ObjCObjectType>();
+ if (object_type) {
+ clang::ObjCInterfaceDecl *interface_decl = object_type->getInterface();
+ if (interface_decl) {
+ interface_decl->startDefinition();
+ return true;
+ }
+ }
+ }
+ return false;
+}
+
+bool ClangASTContext::CompleteTagDeclarationDefinition(
+ const CompilerType &type) {
+ clang::QualType qual_type(ClangUtil::GetQualType(type));
+ if (!qual_type.isNull()) {
+ // Make sure we use the same methodology as
+ // ClangASTContext::StartTagDeclarationDefinition()
+ // as to how we start/end the definition. Previously we were calling
+ const clang::TagType *tag_type = qual_type->getAs<clang::TagType>();
+ if (tag_type) {
+ clang::TagDecl *tag_decl = tag_type->getDecl();
+ if (tag_decl) {
+ clang::CXXRecordDecl *cxx_record_decl =
+ llvm::dyn_cast_or_null<clang::CXXRecordDecl>(tag_decl);
+
+ if (cxx_record_decl) {
+ if (!cxx_record_decl->isCompleteDefinition())
+ cxx_record_decl->completeDefinition();
+ cxx_record_decl->setHasLoadedFieldsFromExternalStorage(true);
+ cxx_record_decl->setHasExternalLexicalStorage(false);
+ cxx_record_decl->setHasExternalVisibleStorage(false);
+ return true;
}
+ }
+ }
- const clang::EnumType *enutype = qual_type->getAs<clang::EnumType>();
-
- if (enutype)
- {
- clang::EnumDecl *enum_decl = enutype->getDecl();
-
- if (enum_decl)
- {
- if (!enum_decl->isCompleteDefinition())
- {
- ClangASTContext *lldb_ast = llvm::dyn_cast<ClangASTContext>(type.GetTypeSystem());
- if (lldb_ast == nullptr)
- return false;
- clang::ASTContext *ast = lldb_ast->getASTContext();
-
- /// TODO This really needs to be fixed.
-
- QualType integer_type(enum_decl->getIntegerType());
- if (!integer_type.isNull())
- {
- unsigned NumPositiveBits = 1;
- unsigned NumNegativeBits = 0;
-
- clang::QualType promotion_qual_type;
- // If the enum integer type is less than an integer in bit width,
- // then we must promote it to an integer size.
- if (ast->getTypeSize(enum_decl->getIntegerType()) < ast->getTypeSize(ast->IntTy))
- {
- if (enum_decl->getIntegerType()->isSignedIntegerType())
- promotion_qual_type = ast->IntTy;
- else
- promotion_qual_type = ast->UnsignedIntTy;
- }
- else
- promotion_qual_type = enum_decl->getIntegerType();
-
- enum_decl->completeDefinition(enum_decl->getIntegerType(), promotion_qual_type, NumPositiveBits, NumNegativeBits);
- }
- }
- return true;
- }
+ const clang::EnumType *enutype = qual_type->getAs<clang::EnumType>();
+
+ if (enutype) {
+ clang::EnumDecl *enum_decl = enutype->getDecl();
+
+ if (enum_decl) {
+ if (!enum_decl->isCompleteDefinition()) {
+ ClangASTContext *lldb_ast =
+ llvm::dyn_cast<ClangASTContext>(type.GetTypeSystem());
+ if (lldb_ast == nullptr)
+ return false;
+ clang::ASTContext *ast = lldb_ast->getASTContext();
+
+ /// TODO This really needs to be fixed.
+
+ QualType integer_type(enum_decl->getIntegerType());
+ if (!integer_type.isNull()) {
+ unsigned NumPositiveBits = 1;
+ unsigned NumNegativeBits = 0;
+
+ clang::QualType promotion_qual_type;
+ // If the enum integer type is less than an integer in bit width,
+ // then we must promote it to an integer size.
+ if (ast->getTypeSize(enum_decl->getIntegerType()) <
+ ast->getTypeSize(ast->IntTy)) {
+ if (enum_decl->getIntegerType()->isSignedIntegerType())
+ promotion_qual_type = ast->IntTy;
+ else
+ promotion_qual_type = ast->UnsignedIntTy;
+ } else
+ promotion_qual_type = enum_decl->getIntegerType();
+
+ enum_decl->completeDefinition(enum_decl->getIntegerType(),
+ promotion_qual_type, NumPositiveBits,
+ NumNegativeBits);
+ }
}
+ return true;
+ }
}
- return false;
+ }
+ return false;
}
-bool
-ClangASTContext::AddEnumerationValueToEnumerationType (lldb::opaque_compiler_type_t type,
- const CompilerType &enumerator_clang_type,
- const Declaration &decl,
- const char *name,
- int64_t enum_value,
- uint32_t enum_value_bit_size)
-{
- if (type && enumerator_clang_type.IsValid() && name && name[0])
- {
- clang::QualType enum_qual_type (GetCanonicalQualType(type));
-
- bool is_signed = false;
- enumerator_clang_type.IsIntegerType (is_signed);
- const clang::Type *clang_type = enum_qual_type.getTypePtr();
- if (clang_type)
- {
- const clang::EnumType *enutype = llvm::dyn_cast<clang::EnumType>(clang_type);
-
- if (enutype)
- {
- llvm::APSInt enum_llvm_apsint(enum_value_bit_size, is_signed);
- enum_llvm_apsint = enum_value;
- clang::EnumConstantDecl *enumerator_decl = clang::EnumConstantDecl::Create(
- *getASTContext(), enutype->getDecl(), clang::SourceLocation(),
- name ? &getASTContext()->Idents.get(name) : nullptr, // Identifier
- ClangUtil::GetQualType(enumerator_clang_type), nullptr, enum_llvm_apsint);
-
- if (enumerator_decl)
- {
- enutype->getDecl()->addDecl(enumerator_decl);
-
+bool ClangASTContext::AddEnumerationValueToEnumerationType(
+ lldb::opaque_compiler_type_t type,
+ const CompilerType &enumerator_clang_type, const Declaration &decl,
+ const char *name, int64_t enum_value, uint32_t enum_value_bit_size) {
+ if (type && enumerator_clang_type.IsValid() && name && name[0]) {
+ clang::QualType enum_qual_type(GetCanonicalQualType(type));
+
+ bool is_signed = false;
+ enumerator_clang_type.IsIntegerType(is_signed);
+ const clang::Type *clang_type = enum_qual_type.getTypePtr();
+ if (clang_type) {
+ const clang::EnumType *enutype =
+ llvm::dyn_cast<clang::EnumType>(clang_type);
+
+ if (enutype) {
+ llvm::APSInt enum_llvm_apsint(enum_value_bit_size, is_signed);
+ enum_llvm_apsint = enum_value;
+ clang::EnumConstantDecl *enumerator_decl =
+ clang::EnumConstantDecl::Create(
+ *getASTContext(), enutype->getDecl(), clang::SourceLocation(),
+ name ? &getASTContext()->Idents.get(name)
+ : nullptr, // Identifier
+ ClangUtil::GetQualType(enumerator_clang_type),
+ nullptr, enum_llvm_apsint);
+
+ if (enumerator_decl) {
+ enutype->getDecl()->addDecl(enumerator_decl);
+
#ifdef LLDB_CONFIGURATION_DEBUG
- VerifyDecl(enumerator_decl);
+ VerifyDecl(enumerator_decl);
#endif
-
- return true;
- }
- }
+
+ return true;
}
+ }
}
- return false;
+ }
+ return false;
}
CompilerType
-ClangASTContext::GetEnumerationIntegerType (lldb::opaque_compiler_type_t type)
-{
- clang::QualType enum_qual_type (GetCanonicalQualType(type));
- const clang::Type *clang_type = enum_qual_type.getTypePtr();
- if (clang_type)
- {
- const clang::EnumType *enutype = llvm::dyn_cast<clang::EnumType>(clang_type);
- if (enutype)
- {
- clang::EnumDecl *enum_decl = enutype->getDecl();
- if (enum_decl)
- return CompilerType (getASTContext(), enum_decl->getIntegerType());
- }
+ClangASTContext::GetEnumerationIntegerType(lldb::opaque_compiler_type_t type) {
+ clang::QualType enum_qual_type(GetCanonicalQualType(type));
+ const clang::Type *clang_type = enum_qual_type.getTypePtr();
+ if (clang_type) {
+ const clang::EnumType *enutype =
+ llvm::dyn_cast<clang::EnumType>(clang_type);
+ if (enutype) {
+ clang::EnumDecl *enum_decl = enutype->getDecl();
+ if (enum_decl)
+ return CompilerType(getASTContext(), enum_decl->getIntegerType());
}
- return CompilerType();
+ }
+ return CompilerType();
}
CompilerType
-ClangASTContext::CreateMemberPointerType (const CompilerType& type, const CompilerType &pointee_type)
-{
- if (type && pointee_type.IsValid() && type.GetTypeSystem() == pointee_type.GetTypeSystem())
- {
- ClangASTContext *ast = llvm::dyn_cast<ClangASTContext>(type.GetTypeSystem());
- if (!ast)
- return CompilerType();
- return CompilerType(ast->getASTContext(),
- ast->getASTContext()->getMemberPointerType(ClangUtil::GetQualType(pointee_type),
- ClangUtil::GetQualType(type).getTypePtr()));
- }
- return CompilerType();
+ClangASTContext::CreateMemberPointerType(const CompilerType &type,
+ const CompilerType &pointee_type) {
+ if (type && pointee_type.IsValid() &&
+ type.GetTypeSystem() == pointee_type.GetTypeSystem()) {
+ ClangASTContext *ast =
+ llvm::dyn_cast<ClangASTContext>(type.GetTypeSystem());
+ if (!ast)
+ return CompilerType();
+ return CompilerType(ast->getASTContext(),
+ ast->getASTContext()->getMemberPointerType(
+ ClangUtil::GetQualType(pointee_type),
+ ClangUtil::GetQualType(type).getTypePtr()));
+ }
+ return CompilerType();
}
-
size_t
-ClangASTContext::ConvertStringToFloatValue (lldb::opaque_compiler_type_t type, const char *s, uint8_t *dst, size_t dst_size)
-{
- if (type)
- {
- clang::QualType qual_type (GetCanonicalQualType(type));
- uint32_t count = 0;
- bool is_complex = false;
- if (IsFloatingPointType (type, count, is_complex))
- {
- // TODO: handle complex and vector types
- if (count != 1)
- return false;
-
- llvm::StringRef s_sref(s);
- llvm::APFloat ap_float(getASTContext()->getFloatTypeSemantics(qual_type), s_sref);
-
- const uint64_t bit_size = getASTContext()->getTypeSize (qual_type);
- const uint64_t byte_size = bit_size / 8;
- if (dst_size >= byte_size)
- {
- Scalar scalar = ap_float.bitcastToAPInt().zextOrTrunc(llvm::NextPowerOf2(byte_size) * 8);
- lldb_private::Error get_data_error;
- if (scalar.GetAsMemoryData(dst, byte_size, lldb_private::endian::InlHostByteOrder(), get_data_error))
- return byte_size;
- }
- }
- }
- return 0;
-}
+ClangASTContext::ConvertStringToFloatValue(lldb::opaque_compiler_type_t type,
+ const char *s, uint8_t *dst,
+ size_t dst_size) {
+ if (type) {
+ clang::QualType qual_type(GetCanonicalQualType(type));
+ uint32_t count = 0;
+ bool is_complex = false;
+ if (IsFloatingPointType(type, count, is_complex)) {
+ // TODO: handle complex and vector types
+ if (count != 1)
+ return false;
+ llvm::StringRef s_sref(s);
+ llvm::APFloat ap_float(getASTContext()->getFloatTypeSemantics(qual_type),
+ s_sref);
+ const uint64_t bit_size = getASTContext()->getTypeSize(qual_type);
+ const uint64_t byte_size = bit_size / 8;
+ if (dst_size >= byte_size) {
+ Scalar scalar = ap_float.bitcastToAPInt().zextOrTrunc(
+ llvm::NextPowerOf2(byte_size) * 8);
+ lldb_private::Error get_data_error;
+ if (scalar.GetAsMemoryData(dst, byte_size,
+ lldb_private::endian::InlHostByteOrder(),
+ get_data_error))
+ return byte_size;
+ }
+ }
+ }
+ return 0;
+}
//----------------------------------------------------------------------
// Dumping types
//----------------------------------------------------------------------
#define DEPTH_INCREMENT 2
-void
-ClangASTContext::DumpValue (lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx,
- Stream *s,
- lldb::Format format,
- const lldb_private::DataExtractor &data,
- lldb::offset_t data_byte_offset,
- size_t data_byte_size,
- uint32_t bitfield_bit_size,
- uint32_t bitfield_bit_offset,
- bool show_types,
- bool show_summary,
- bool verbose,
- uint32_t depth)
-{
- if (!type)
- return;
-
+void ClangASTContext::DumpValue(
+ lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx, Stream *s,
+ lldb::Format format, const lldb_private::DataExtractor &data,
+ lldb::offset_t data_byte_offset, size_t data_byte_size,
+ uint32_t bitfield_bit_size, uint32_t bitfield_bit_offset, bool show_types,
+ bool show_summary, bool verbose, uint32_t depth) {
+ if (!type)
+ return;
+
+ clang::QualType qual_type(GetQualType(type));
+ switch (qual_type->getTypeClass()) {
+ case clang::Type::Record:
+ if (GetCompleteType(type)) {
+ const clang::RecordType *record_type =
+ llvm::cast<clang::RecordType>(qual_type.getTypePtr());
+ const clang::RecordDecl *record_decl = record_type->getDecl();
+ assert(record_decl);
+ uint32_t field_bit_offset = 0;
+ uint32_t field_byte_offset = 0;
+ const clang::ASTRecordLayout &record_layout =
+ getASTContext()->getASTRecordLayout(record_decl);
+ uint32_t child_idx = 0;
+
+ const clang::CXXRecordDecl *cxx_record_decl =
+ llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
+ if (cxx_record_decl) {
+ // We might have base classes to print out first
+ clang::CXXRecordDecl::base_class_const_iterator base_class,
+ base_class_end;
+ for (base_class = cxx_record_decl->bases_begin(),
+ base_class_end = cxx_record_decl->bases_end();
+ base_class != base_class_end; ++base_class) {
+ const clang::CXXRecordDecl *base_class_decl =
+ llvm::cast<clang::CXXRecordDecl>(
+ base_class->getType()->getAs<clang::RecordType>()->getDecl());
+
+ // Skip empty base classes
+ if (verbose == false &&
+ ClangASTContext::RecordHasFields(base_class_decl) == false)
+ continue;
+
+ if (base_class->isVirtual())
+ field_bit_offset =
+ record_layout.getVBaseClassOffset(base_class_decl)
+ .getQuantity() *
+ 8;
+ else
+ field_bit_offset = record_layout.getBaseClassOffset(base_class_decl)
+ .getQuantity() *
+ 8;
+ field_byte_offset = field_bit_offset / 8;
+ assert(field_bit_offset % 8 == 0);
+ if (child_idx == 0)
+ s->PutChar('{');
+ else
+ s->PutChar(',');
+
+ clang::QualType base_class_qual_type = base_class->getType();
+ std::string base_class_type_name(base_class_qual_type.getAsString());
+
+ // Indent and print the base class type name
+ s->Printf("\n%*s%s ", depth + DEPTH_INCREMENT, "",
+ base_class_type_name.c_str());
+
+ clang::TypeInfo base_class_type_info =
+ getASTContext()->getTypeInfo(base_class_qual_type);
+
+ // Dump the value of the member
+ CompilerType base_clang_type(getASTContext(), base_class_qual_type);
+ base_clang_type.DumpValue(
+ exe_ctx,
+ s, // Stream to dump to
+ base_clang_type
+ .GetFormat(), // The format with which to display the member
+ data, // Data buffer containing all bytes for this type
+ data_byte_offset + field_byte_offset, // Offset into "data" where
+ // to grab value from
+ base_class_type_info.Width / 8, // Size of this type in bytes
+ 0, // Bitfield bit size
+ 0, // Bitfield bit offset
+ show_types, // Boolean indicating if we should show the variable
+ // types
+ show_summary, // Boolean indicating if we should show a summary
+ // for the current type
+ verbose, // Verbose output?
+ depth + DEPTH_INCREMENT); // Scope depth for any types that have
+ // children
+
+ ++child_idx;
+ }
+ }
+ uint32_t field_idx = 0;
+ clang::RecordDecl::field_iterator field, field_end;
+ for (field = record_decl->field_begin(),
+ field_end = record_decl->field_end();
+ field != field_end; ++field, ++field_idx, ++child_idx) {
+ // Print the starting squiggly bracket (if this is the
+ // first member) or comma (for member 2 and beyond) for
+ // the struct/union/class member.
+ if (child_idx == 0)
+ s->PutChar('{');
+ else
+ s->PutChar(',');
+
+ // Indent
+ s->Printf("\n%*s", depth + DEPTH_INCREMENT, "");
+
+ clang::QualType field_type = field->getType();
+ // Print the member type if requested
+ // Figure out the type byte size (field_type_info.first) and
+ // alignment (field_type_info.second) from the AST context.
+ clang::TypeInfo field_type_info =
+ getASTContext()->getTypeInfo(field_type);
+ assert(field_idx < record_layout.getFieldCount());
+ // Figure out the field offset within the current struct/union/class
+ // type
+ field_bit_offset = record_layout.getFieldOffset(field_idx);
+ field_byte_offset = field_bit_offset / 8;
+ uint32_t field_bitfield_bit_size = 0;
+ uint32_t field_bitfield_bit_offset = 0;
+ if (ClangASTContext::FieldIsBitfield(getASTContext(), *field,
+ field_bitfield_bit_size))
+ field_bitfield_bit_offset = field_bit_offset % 8;
+
+ if (show_types) {
+ std::string field_type_name(field_type.getAsString());
+ if (field_bitfield_bit_size > 0)
+ s->Printf("(%s:%u) ", field_type_name.c_str(),
+ field_bitfield_bit_size);
+ else
+ s->Printf("(%s) ", field_type_name.c_str());
+ }
+ // Print the member name and equal sign
+ s->Printf("%s = ", field->getNameAsString().c_str());
+
+ // Dump the value of the member
+ CompilerType field_clang_type(getASTContext(), field_type);
+ field_clang_type.DumpValue(
+ exe_ctx,
+ s, // Stream to dump to
+ field_clang_type
+ .GetFormat(), // The format with which to display the member
+ data, // Data buffer containing all bytes for this type
+ data_byte_offset + field_byte_offset, // Offset into "data" where to
+ // grab value from
+ field_type_info.Width / 8, // Size of this type in bytes
+ field_bitfield_bit_size, // Bitfield bit size
+ field_bitfield_bit_offset, // Bitfield bit offset
+ show_types, // Boolean indicating if we should show the variable
+ // types
+ show_summary, // Boolean indicating if we should show a summary for
+ // the current type
+ verbose, // Verbose output?
+ depth + DEPTH_INCREMENT); // Scope depth for any types that have
+ // children
+ }
+
+ // Indent the trailing squiggly bracket
+ if (child_idx > 0)
+ s->Printf("\n%*s}", depth, "");
+ }
+ return;
+
+ case clang::Type::Enum:
+ if (GetCompleteType(type)) {
+ const clang::EnumType *enutype =
+ llvm::cast<clang::EnumType>(qual_type.getTypePtr());
+ const clang::EnumDecl *enum_decl = enutype->getDecl();
+ assert(enum_decl);
+ clang::EnumDecl::enumerator_iterator enum_pos, enum_end_pos;
+ lldb::offset_t offset = data_byte_offset;
+ const int64_t enum_value = data.GetMaxU64Bitfield(
+ &offset, data_byte_size, bitfield_bit_size, bitfield_bit_offset);
+ for (enum_pos = enum_decl->enumerator_begin(),
+ enum_end_pos = enum_decl->enumerator_end();
+ enum_pos != enum_end_pos; ++enum_pos) {
+ if (enum_pos->getInitVal() == enum_value) {
+ s->Printf("%s", enum_pos->getNameAsString().c_str());
+ return;
+ }
+ }
+ // If we have gotten here we didn't get find the enumerator in the
+ // enum decl, so just print the integer.
+ s->Printf("%" PRIi64, enum_value);
+ }
+ return;
+
+ case clang::Type::ConstantArray: {
+ const clang::ConstantArrayType *array =
+ llvm::cast<clang::ConstantArrayType>(qual_type.getTypePtr());
+ bool is_array_of_characters = false;
+ clang::QualType element_qual_type = array->getElementType();
+
+ const clang::Type *canonical_type =
+ element_qual_type->getCanonicalTypeInternal().getTypePtr();
+ if (canonical_type)
+ is_array_of_characters = canonical_type->isCharType();
+
+ const uint64_t element_count = array->getSize().getLimitedValue();
+
+ clang::TypeInfo field_type_info =
+ getASTContext()->getTypeInfo(element_qual_type);
+
+ uint32_t element_idx = 0;
+ uint32_t element_offset = 0;
+ uint64_t element_byte_size = field_type_info.Width / 8;
+ uint32_t element_stride = element_byte_size;
+
+ if (is_array_of_characters) {
+ s->PutChar('"');
+ data.Dump(s, data_byte_offset, lldb::eFormatChar, element_byte_size,
+ element_count, UINT32_MAX, LLDB_INVALID_ADDRESS, 0, 0);
+ s->PutChar('"');
+ return;
+ } else {
+ CompilerType element_clang_type(getASTContext(), element_qual_type);
+ lldb::Format element_format = element_clang_type.GetFormat();
+
+ for (element_idx = 0; element_idx < element_count; ++element_idx) {
+ // Print the starting squiggly bracket (if this is the
+ // first member) or comman (for member 2 and beyong) for
+ // the struct/union/class member.
+ if (element_idx == 0)
+ s->PutChar('{');
+ else
+ s->PutChar(',');
+
+ // Indent and print the index
+ s->Printf("\n%*s[%u] ", depth + DEPTH_INCREMENT, "", element_idx);
+
+ // Figure out the field offset within the current struct/union/class
+ // type
+ element_offset = element_idx * element_stride;
+
+ // Dump the value of the member
+ element_clang_type.DumpValue(
+ exe_ctx,
+ s, // Stream to dump to
+ element_format, // The format with which to display the element
+ data, // Data buffer containing all bytes for this type
+ data_byte_offset +
+ element_offset, // Offset into "data" where to grab value from
+ element_byte_size, // Size of this type in bytes
+ 0, // Bitfield bit size
+ 0, // Bitfield bit offset
+ show_types, // Boolean indicating if we should show the variable
+ // types
+ show_summary, // Boolean indicating if we should show a summary for
+ // the current type
+ verbose, // Verbose output?
+ depth + DEPTH_INCREMENT); // Scope depth for any types that have
+ // children
+ }
+
+ // Indent the trailing squiggly bracket
+ if (element_idx > 0)
+ s->Printf("\n%*s}", depth, "");
+ }
+ }
+ return;
+
+ case clang::Type::Typedef: {
+ clang::QualType typedef_qual_type =
+ llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType();
+
+ CompilerType typedef_clang_type(getASTContext(), typedef_qual_type);
+ lldb::Format typedef_format = typedef_clang_type.GetFormat();
+ clang::TypeInfo typedef_type_info =
+ getASTContext()->getTypeInfo(typedef_qual_type);
+ uint64_t typedef_byte_size = typedef_type_info.Width / 8;
+
+ return typedef_clang_type.DumpValue(
+ exe_ctx,
+ s, // Stream to dump to
+ typedef_format, // The format with which to display the element
+ data, // Data buffer containing all bytes for this type
+ data_byte_offset, // Offset into "data" where to grab value from
+ typedef_byte_size, // Size of this type in bytes
+ bitfield_bit_size, // Bitfield bit size
+ bitfield_bit_offset, // Bitfield bit offset
+ show_types, // Boolean indicating if we should show the variable types
+ show_summary, // Boolean indicating if we should show a summary for the
+ // current type
+ verbose, // Verbose output?
+ depth); // Scope depth for any types that have children
+ } break;
+
+ case clang::Type::Auto: {
+ clang::QualType elaborated_qual_type =
+ llvm::cast<clang::AutoType>(qual_type)->getDeducedType();
+ CompilerType elaborated_clang_type(getASTContext(), elaborated_qual_type);
+ lldb::Format elaborated_format = elaborated_clang_type.GetFormat();
+ clang::TypeInfo elaborated_type_info =
+ getASTContext()->getTypeInfo(elaborated_qual_type);
+ uint64_t elaborated_byte_size = elaborated_type_info.Width / 8;
+
+ return elaborated_clang_type.DumpValue(
+ exe_ctx,
+ s, // Stream to dump to
+ elaborated_format, // The format with which to display the element
+ data, // Data buffer containing all bytes for this type
+ data_byte_offset, // Offset into "data" where to grab value from
+ elaborated_byte_size, // Size of this type in bytes
+ bitfield_bit_size, // Bitfield bit size
+ bitfield_bit_offset, // Bitfield bit offset
+ show_types, // Boolean indicating if we should show the variable types
+ show_summary, // Boolean indicating if we should show a summary for the
+ // current type
+ verbose, // Verbose output?
+ depth); // Scope depth for any types that have children
+ } break;
+
+ case clang::Type::Elaborated: {
+ clang::QualType elaborated_qual_type =
+ llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType();
+ CompilerType elaborated_clang_type(getASTContext(), elaborated_qual_type);
+ lldb::Format elaborated_format = elaborated_clang_type.GetFormat();
+ clang::TypeInfo elaborated_type_info =
+ getASTContext()->getTypeInfo(elaborated_qual_type);
+ uint64_t elaborated_byte_size = elaborated_type_info.Width / 8;
+
+ return elaborated_clang_type.DumpValue(
+ exe_ctx,
+ s, // Stream to dump to
+ elaborated_format, // The format with which to display the element
+ data, // Data buffer containing all bytes for this type
+ data_byte_offset, // Offset into "data" where to grab value from
+ elaborated_byte_size, // Size of this type in bytes
+ bitfield_bit_size, // Bitfield bit size
+ bitfield_bit_offset, // Bitfield bit offset
+ show_types, // Boolean indicating if we should show the variable types
+ show_summary, // Boolean indicating if we should show a summary for the
+ // current type
+ verbose, // Verbose output?
+ depth); // Scope depth for any types that have children
+ } break;
+
+ case clang::Type::Paren: {
+ clang::QualType desugar_qual_type =
+ llvm::cast<clang::ParenType>(qual_type)->desugar();
+ CompilerType desugar_clang_type(getASTContext(), desugar_qual_type);
+
+ lldb::Format desugar_format = desugar_clang_type.GetFormat();
+ clang::TypeInfo desugar_type_info =
+ getASTContext()->getTypeInfo(desugar_qual_type);
+ uint64_t desugar_byte_size = desugar_type_info.Width / 8;
+
+ return desugar_clang_type.DumpValue(
+ exe_ctx,
+ s, // Stream to dump to
+ desugar_format, // The format with which to display the element
+ data, // Data buffer containing all bytes for this type
+ data_byte_offset, // Offset into "data" where to grab value from
+ desugar_byte_size, // Size of this type in bytes
+ bitfield_bit_size, // Bitfield bit size
+ bitfield_bit_offset, // Bitfield bit offset
+ show_types, // Boolean indicating if we should show the variable types
+ show_summary, // Boolean indicating if we should show a summary for the
+ // current type
+ verbose, // Verbose output?
+ depth); // Scope depth for any types that have children
+ } break;
+
+ default:
+ // We are down to a scalar type that we just need to display.
+ data.Dump(s, data_byte_offset, format, data_byte_size, 1, UINT32_MAX,
+ LLDB_INVALID_ADDRESS, bitfield_bit_size, bitfield_bit_offset);
+
+ if (show_summary)
+ DumpSummary(type, exe_ctx, s, data, data_byte_offset, data_byte_size);
+ break;
+ }
+}
+
+bool ClangASTContext::DumpTypeValue(
+ lldb::opaque_compiler_type_t type, Stream *s, lldb::Format format,
+ const lldb_private::DataExtractor &data, lldb::offset_t byte_offset,
+ size_t byte_size, uint32_t bitfield_bit_size, uint32_t bitfield_bit_offset,
+ ExecutionContextScope *exe_scope) {
+ if (!type)
+ return false;
+ if (IsAggregateType(type)) {
+ return false;
+ } else {
clang::QualType qual_type(GetQualType(type));
- switch (qual_type->getTypeClass())
- {
- case clang::Type::Record:
- if (GetCompleteType(type))
- {
- const clang::RecordType *record_type = llvm::cast<clang::RecordType>(qual_type.getTypePtr());
- const clang::RecordDecl *record_decl = record_type->getDecl();
- assert(record_decl);
- uint32_t field_bit_offset = 0;
- uint32_t field_byte_offset = 0;
- const clang::ASTRecordLayout &record_layout = getASTContext()->getASTRecordLayout(record_decl);
- uint32_t child_idx = 0;
-
- const clang::CXXRecordDecl *cxx_record_decl = llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
- if (cxx_record_decl)
- {
- // We might have base classes to print out first
- clang::CXXRecordDecl::base_class_const_iterator base_class, base_class_end;
- for (base_class = cxx_record_decl->bases_begin(), base_class_end = cxx_record_decl->bases_end();
- base_class != base_class_end;
- ++base_class)
- {
- const clang::CXXRecordDecl *base_class_decl = llvm::cast<clang::CXXRecordDecl>(base_class->getType()->getAs<clang::RecordType>()->getDecl());
-
- // Skip empty base classes
- if (verbose == false && ClangASTContext::RecordHasFields(base_class_decl) == false)
- continue;
-
- if (base_class->isVirtual())
- field_bit_offset = record_layout.getVBaseClassOffset(base_class_decl).getQuantity() * 8;
- else
- field_bit_offset = record_layout.getBaseClassOffset(base_class_decl).getQuantity() * 8;
- field_byte_offset = field_bit_offset / 8;
- assert (field_bit_offset % 8 == 0);
- if (child_idx == 0)
- s->PutChar('{');
- else
- s->PutChar(',');
-
- clang::QualType base_class_qual_type = base_class->getType();
- std::string base_class_type_name(base_class_qual_type.getAsString());
-
- // Indent and print the base class type name
- s->Printf("\n%*s%s ", depth + DEPTH_INCREMENT, "", base_class_type_name.c_str());
-
- clang::TypeInfo base_class_type_info = getASTContext()->getTypeInfo(base_class_qual_type);
-
- // Dump the value of the member
- CompilerType base_clang_type(getASTContext(), base_class_qual_type);
- base_clang_type.DumpValue (exe_ctx,
- s, // Stream to dump to
- base_clang_type.GetFormat(), // The format with which to display the member
- data, // Data buffer containing all bytes for this type
- data_byte_offset + field_byte_offset,// Offset into "data" where to grab value from
- base_class_type_info.Width / 8, // Size of this type in bytes
- 0, // Bitfield bit size
- 0, // Bitfield bit offset
- show_types, // Boolean indicating if we should show the variable types
- show_summary, // Boolean indicating if we should show a summary for the current type
- verbose, // Verbose output?
- depth + DEPTH_INCREMENT); // Scope depth for any types that have children
-
- ++child_idx;
- }
- }
- uint32_t field_idx = 0;
- clang::RecordDecl::field_iterator field, field_end;
- for (field = record_decl->field_begin(), field_end = record_decl->field_end(); field != field_end; ++field, ++field_idx, ++child_idx)
- {
- // Print the starting squiggly bracket (if this is the
- // first member) or comma (for member 2 and beyond) for
- // the struct/union/class member.
- if (child_idx == 0)
- s->PutChar('{');
- else
- s->PutChar(',');
-
- // Indent
- s->Printf("\n%*s", depth + DEPTH_INCREMENT, "");
-
- clang::QualType field_type = field->getType();
- // Print the member type if requested
- // Figure out the type byte size (field_type_info.first) and
- // alignment (field_type_info.second) from the AST context.
- clang::TypeInfo field_type_info = getASTContext()->getTypeInfo(field_type);
- assert(field_idx < record_layout.getFieldCount());
- // Figure out the field offset within the current struct/union/class type
- field_bit_offset = record_layout.getFieldOffset (field_idx);
- field_byte_offset = field_bit_offset / 8;
- uint32_t field_bitfield_bit_size = 0;
- uint32_t field_bitfield_bit_offset = 0;
- if (ClangASTContext::FieldIsBitfield (getASTContext(), *field, field_bitfield_bit_size))
- field_bitfield_bit_offset = field_bit_offset % 8;
-
- if (show_types)
- {
- std::string field_type_name(field_type.getAsString());
- if (field_bitfield_bit_size > 0)
- s->Printf("(%s:%u) ", field_type_name.c_str(), field_bitfield_bit_size);
- else
- s->Printf("(%s) ", field_type_name.c_str());
- }
- // Print the member name and equal sign
- s->Printf("%s = ", field->getNameAsString().c_str());
-
-
- // Dump the value of the member
- CompilerType field_clang_type (getASTContext(), field_type);
- field_clang_type.DumpValue (exe_ctx,
- s, // Stream to dump to
- field_clang_type.GetFormat(), // The format with which to display the member
- data, // Data buffer containing all bytes for this type
- data_byte_offset + field_byte_offset,// Offset into "data" where to grab value from
- field_type_info.Width / 8, // Size of this type in bytes
- field_bitfield_bit_size, // Bitfield bit size
- field_bitfield_bit_offset, // Bitfield bit offset
- show_types, // Boolean indicating if we should show the variable types
- show_summary, // Boolean indicating if we should show a summary for the current type
- verbose, // Verbose output?
- depth + DEPTH_INCREMENT); // Scope depth for any types that have children
- }
-
- // Indent the trailing squiggly bracket
- if (child_idx > 0)
- s->Printf("\n%*s}", depth, "");
- }
- return;
-
- case clang::Type::Enum:
- if (GetCompleteType(type))
- {
- const clang::EnumType *enutype = llvm::cast<clang::EnumType>(qual_type.getTypePtr());
- const clang::EnumDecl *enum_decl = enutype->getDecl();
- assert(enum_decl);
- clang::EnumDecl::enumerator_iterator enum_pos, enum_end_pos;
- lldb::offset_t offset = data_byte_offset;
- const int64_t enum_value = data.GetMaxU64Bitfield(&offset, data_byte_size, bitfield_bit_size, bitfield_bit_offset);
- for (enum_pos = enum_decl->enumerator_begin(), enum_end_pos = enum_decl->enumerator_end(); enum_pos != enum_end_pos; ++enum_pos)
- {
- if (enum_pos->getInitVal() == enum_value)
- {
- s->Printf("%s", enum_pos->getNameAsString().c_str());
- return;
- }
- }
- // If we have gotten here we didn't get find the enumerator in the
- // enum decl, so just print the integer.
- s->Printf("%" PRIi64, enum_value);
+
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Typedef: {
+ clang::QualType typedef_qual_type =
+ llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getUnderlyingType();
+ CompilerType typedef_clang_type(getASTContext(), typedef_qual_type);
+ if (format == eFormatDefault)
+ format = typedef_clang_type.GetFormat();
+ clang::TypeInfo typedef_type_info =
+ getASTContext()->getTypeInfo(typedef_qual_type);
+ uint64_t typedef_byte_size = typedef_type_info.Width / 8;
+
+ return typedef_clang_type.DumpTypeValue(
+ s,
+ format, // The format with which to display the element
+ data, // Data buffer containing all bytes for this type
+ byte_offset, // Offset into "data" where to grab value from
+ typedef_byte_size, // Size of this type in bytes
+ bitfield_bit_size, // Size in bits of a bitfield value, if zero don't
+ // treat as a bitfield
+ bitfield_bit_offset, // Offset in bits of a bitfield value if
+ // bitfield_bit_size != 0
+ exe_scope);
+ } break;
+
+ case clang::Type::Enum:
+ // If our format is enum or default, show the enumeration value as
+ // its enumeration string value, else just display it as requested.
+ if ((format == eFormatEnum || format == eFormatDefault) &&
+ GetCompleteType(type)) {
+ const clang::EnumType *enutype =
+ llvm::cast<clang::EnumType>(qual_type.getTypePtr());
+ const clang::EnumDecl *enum_decl = enutype->getDecl();
+ assert(enum_decl);
+ clang::EnumDecl::enumerator_iterator enum_pos, enum_end_pos;
+ const bool is_signed = qual_type->isSignedIntegerOrEnumerationType();
+ lldb::offset_t offset = byte_offset;
+ if (is_signed) {
+ const int64_t enum_svalue = data.GetMaxS64Bitfield(
+ &offset, byte_size, bitfield_bit_size, bitfield_bit_offset);
+ for (enum_pos = enum_decl->enumerator_begin(),
+ enum_end_pos = enum_decl->enumerator_end();
+ enum_pos != enum_end_pos; ++enum_pos) {
+ if (enum_pos->getInitVal().getSExtValue() == enum_svalue) {
+ s->PutCString(enum_pos->getNameAsString().c_str());
+ return true;
}
- return;
-
- case clang::Type::ConstantArray:
- {
- const clang::ConstantArrayType *array = llvm::cast<clang::ConstantArrayType>(qual_type.getTypePtr());
- bool is_array_of_characters = false;
- clang::QualType element_qual_type = array->getElementType();
-
- const clang::Type *canonical_type = element_qual_type->getCanonicalTypeInternal().getTypePtr();
- if (canonical_type)
- is_array_of_characters = canonical_type->isCharType();
-
- const uint64_t element_count = array->getSize().getLimitedValue();
-
- clang::TypeInfo field_type_info = getASTContext()->getTypeInfo(element_qual_type);
-
- uint32_t element_idx = 0;
- uint32_t element_offset = 0;
- uint64_t element_byte_size = field_type_info.Width / 8;
- uint32_t element_stride = element_byte_size;
-
- if (is_array_of_characters)
- {
- s->PutChar('"');
- data.Dump(s, data_byte_offset, lldb::eFormatChar, element_byte_size, element_count, UINT32_MAX, LLDB_INVALID_ADDRESS, 0, 0);
- s->PutChar('"');
- return;
+ }
+ // If we have gotten here we didn't get find the enumerator in the
+ // enum decl, so just print the integer.
+ s->Printf("%" PRIi64, enum_svalue);
+ } else {
+ const uint64_t enum_uvalue = data.GetMaxU64Bitfield(
+ &offset, byte_size, bitfield_bit_size, bitfield_bit_offset);
+ for (enum_pos = enum_decl->enumerator_begin(),
+ enum_end_pos = enum_decl->enumerator_end();
+ enum_pos != enum_end_pos; ++enum_pos) {
+ if (enum_pos->getInitVal().getZExtValue() == enum_uvalue) {
+ s->PutCString(enum_pos->getNameAsString().c_str());
+ return true;
}
- else
- {
- CompilerType element_clang_type(getASTContext(), element_qual_type);
- lldb::Format element_format = element_clang_type.GetFormat();
-
- for (element_idx = 0; element_idx < element_count; ++element_idx)
- {
- // Print the starting squiggly bracket (if this is the
- // first member) or comman (for member 2 and beyong) for
- // the struct/union/class member.
- if (element_idx == 0)
- s->PutChar('{');
- else
- s->PutChar(',');
-
- // Indent and print the index
- s->Printf("\n%*s[%u] ", depth + DEPTH_INCREMENT, "", element_idx);
-
- // Figure out the field offset within the current struct/union/class type
- element_offset = element_idx * element_stride;
-
- // Dump the value of the member
- element_clang_type.DumpValue (exe_ctx,
- s, // Stream to dump to
- element_format, // The format with which to display the element
- data, // Data buffer containing all bytes for this type
- data_byte_offset + element_offset,// Offset into "data" where to grab value from
- element_byte_size, // Size of this type in bytes
- 0, // Bitfield bit size
- 0, // Bitfield bit offset
- show_types, // Boolean indicating if we should show the variable types
- show_summary, // Boolean indicating if we should show a summary for the current type
- verbose, // Verbose output?
- depth + DEPTH_INCREMENT); // Scope depth for any types that have children
- }
-
- // Indent the trailing squiggly bracket
- if (element_idx > 0)
- s->Printf("\n%*s}", depth, "");
- }
- }
- return;
-
- case clang::Type::Typedef:
- {
- clang::QualType typedef_qual_type = llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType();
-
- CompilerType typedef_clang_type (getASTContext(), typedef_qual_type);
- lldb::Format typedef_format = typedef_clang_type.GetFormat();
- clang::TypeInfo typedef_type_info = getASTContext()->getTypeInfo(typedef_qual_type);
- uint64_t typedef_byte_size = typedef_type_info.Width / 8;
-
- return typedef_clang_type.DumpValue (exe_ctx,
- s, // Stream to dump to
- typedef_format, // The format with which to display the element
- data, // Data buffer containing all bytes for this type
- data_byte_offset, // Offset into "data" where to grab value from
- typedef_byte_size, // Size of this type in bytes
- bitfield_bit_size, // Bitfield bit size
- bitfield_bit_offset,// Bitfield bit offset
- show_types, // Boolean indicating if we should show the variable types
- show_summary, // Boolean indicating if we should show a summary for the current type
- verbose, // Verbose output?
- depth); // Scope depth for any types that have children
+ }
+ // If we have gotten here we didn't get find the enumerator in the
+ // enum decl, so just print the integer.
+ s->Printf("%" PRIu64, enum_uvalue);
}
- break;
-
- case clang::Type::Auto:
- {
- clang::QualType elaborated_qual_type = llvm::cast<clang::AutoType>(qual_type)->getDeducedType();
- CompilerType elaborated_clang_type (getASTContext(), elaborated_qual_type);
- lldb::Format elaborated_format = elaborated_clang_type.GetFormat();
- clang::TypeInfo elaborated_type_info = getASTContext()->getTypeInfo(elaborated_qual_type);
- uint64_t elaborated_byte_size = elaborated_type_info.Width / 8;
-
- return elaborated_clang_type.DumpValue (exe_ctx,
- s, // Stream to dump to
- elaborated_format, // The format with which to display the element
- data, // Data buffer containing all bytes for this type
- data_byte_offset, // Offset into "data" where to grab value from
- elaborated_byte_size, // Size of this type in bytes
- bitfield_bit_size, // Bitfield bit size
- bitfield_bit_offset,// Bitfield bit offset
- show_types, // Boolean indicating if we should show the variable types
- show_summary, // Boolean indicating if we should show a summary for the current type
- verbose, // Verbose output?
- depth); // Scope depth for any types that have children
+ return true;
+ }
+ // format was not enum, just fall through and dump the value as
+ // requested....
+ LLVM_FALLTHROUGH;
+
+ default:
+ // We are down to a scalar type that we just need to display.
+ {
+ uint32_t item_count = 1;
+ // A few formats, we might need to modify our size and count for
+ // depending
+ // on how we are trying to display the value...
+ switch (format) {
+ default:
+ case eFormatBoolean:
+ case eFormatBinary:
+ case eFormatComplex:
+ case eFormatCString: // NULL terminated C strings
+ case eFormatDecimal:
+ case eFormatEnum:
+ case eFormatHex:
+ case eFormatHexUppercase:
+ case eFormatFloat:
+ case eFormatOctal:
+ case eFormatOSType:
+ case eFormatUnsigned:
+ case eFormatPointer:
+ case eFormatVectorOfChar:
+ case eFormatVectorOfSInt8:
+ case eFormatVectorOfUInt8:
+ case eFormatVectorOfSInt16:
+ case eFormatVectorOfUInt16:
+ case eFormatVectorOfSInt32:
+ case eFormatVectorOfUInt32:
+ case eFormatVectorOfSInt64:
+ case eFormatVectorOfUInt64:
+ case eFormatVectorOfFloat32:
+ case eFormatVectorOfFloat64:
+ case eFormatVectorOfUInt128:
+ break;
+
+ case eFormatChar:
+ case eFormatCharPrintable:
+ case eFormatCharArray:
+ case eFormatBytes:
+ case eFormatBytesWithASCII:
+ item_count = byte_size;
+ byte_size = 1;
+ break;
+
+ case eFormatUnicode16:
+ item_count = byte_size / 2;
+ byte_size = 2;
+ break;
+
+ case eFormatUnicode32:
+ item_count = byte_size / 4;
+ byte_size = 4;
+ break;
}
+ return data.Dump(s, byte_offset, format, byte_size, item_count,
+ UINT32_MAX, LLDB_INVALID_ADDRESS, bitfield_bit_size,
+ bitfield_bit_offset, exe_scope);
+ }
+ break;
+ }
+ }
+ return 0;
+}
+
+void ClangASTContext::DumpSummary(lldb::opaque_compiler_type_t type,
+ ExecutionContext *exe_ctx, Stream *s,
+ const lldb_private::DataExtractor &data,
+ lldb::offset_t data_byte_offset,
+ size_t data_byte_size) {
+ uint32_t length = 0;
+ if (IsCStringType(type, length)) {
+ if (exe_ctx) {
+ Process *process = exe_ctx->GetProcessPtr();
+ if (process) {
+ lldb::offset_t offset = data_byte_offset;
+ lldb::addr_t pointer_address = data.GetMaxU64(&offset, data_byte_size);
+ std::vector<uint8_t> buf;
+ if (length > 0)
+ buf.resize(length);
+ else
+ buf.resize(256);
+
+ lldb_private::DataExtractor cstr_data(&buf.front(), buf.size(),
+ process->GetByteOrder(), 4);
+ buf.back() = '\0';
+ size_t bytes_read;
+ size_t total_cstr_len = 0;
+ Error error;
+ while ((bytes_read = process->ReadMemory(pointer_address, &buf.front(),
+ buf.size(), error)) > 0) {
+ const size_t len = strlen((const char *)&buf.front());
+ if (len == 0)
break;
-
- case clang::Type::Elaborated:
- {
- clang::QualType elaborated_qual_type = llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType();
- CompilerType elaborated_clang_type (getASTContext(), elaborated_qual_type);
- lldb::Format elaborated_format = elaborated_clang_type.GetFormat();
- clang::TypeInfo elaborated_type_info = getASTContext()->getTypeInfo(elaborated_qual_type);
- uint64_t elaborated_byte_size = elaborated_type_info.Width / 8;
-
- return elaborated_clang_type.DumpValue (exe_ctx,
- s, // Stream to dump to
- elaborated_format, // The format with which to display the element
- data, // Data buffer containing all bytes for this type
- data_byte_offset, // Offset into "data" where to grab value from
- elaborated_byte_size, // Size of this type in bytes
- bitfield_bit_size, // Bitfield bit size
- bitfield_bit_offset,// Bitfield bit offset
- show_types, // Boolean indicating if we should show the variable types
- show_summary, // Boolean indicating if we should show a summary for the current type
- verbose, // Verbose output?
- depth); // Scope depth for any types that have children
- }
+ if (total_cstr_len == 0)
+ s->PutCString(" \"");
+ cstr_data.Dump(s, 0, lldb::eFormatChar, 1, len, UINT32_MAX,
+ LLDB_INVALID_ADDRESS, 0, 0);
+ total_cstr_len += len;
+ if (len < buf.size())
break;
-
- case clang::Type::Paren:
- {
- clang::QualType desugar_qual_type = llvm::cast<clang::ParenType>(qual_type)->desugar();
- CompilerType desugar_clang_type (getASTContext(), desugar_qual_type);
-
- lldb::Format desugar_format = desugar_clang_type.GetFormat();
- clang::TypeInfo desugar_type_info = getASTContext()->getTypeInfo(desugar_qual_type);
- uint64_t desugar_byte_size = desugar_type_info.Width / 8;
-
- return desugar_clang_type.DumpValue (exe_ctx,
- s, // Stream to dump to
- desugar_format, // The format with which to display the element
- data, // Data buffer containing all bytes for this type
- data_byte_offset, // Offset into "data" where to grab value from
- desugar_byte_size, // Size of this type in bytes
- bitfield_bit_size, // Bitfield bit size
- bitfield_bit_offset,// Bitfield bit offset
- show_types, // Boolean indicating if we should show the variable types
- show_summary, // Boolean indicating if we should show a summary for the current type
- verbose, // Verbose output?
- depth); // Scope depth for any types that have children
+ pointer_address += total_cstr_len;
}
- break;
-
- default:
- // We are down to a scalar type that we just need to display.
- data.Dump(s,
- data_byte_offset,
- format,
- data_byte_size,
- 1,
- UINT32_MAX,
- LLDB_INVALID_ADDRESS,
- bitfield_bit_size,
- bitfield_bit_offset);
-
- if (show_summary)
- DumpSummary (type, exe_ctx, s, data, data_byte_offset, data_byte_size);
- break;
+ if (total_cstr_len > 0)
+ s->PutChar('"');
+ }
}
+ }
}
-
-
-
-bool
-ClangASTContext::DumpTypeValue (lldb::opaque_compiler_type_t type, Stream *s,
- lldb::Format format,
- const lldb_private::DataExtractor &data,
- lldb::offset_t byte_offset,
- size_t byte_size,
- uint32_t bitfield_bit_size,
- uint32_t bitfield_bit_offset,
- ExecutionContextScope *exe_scope)
-{
- if (!type)
- return false;
- if (IsAggregateType(type))
- {
- return false;
- }
- else
- {
- clang::QualType qual_type(GetQualType(type));
-
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Typedef:
- {
- clang::QualType typedef_qual_type = llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getUnderlyingType();
- CompilerType typedef_clang_type (getASTContext(), typedef_qual_type);
- if (format == eFormatDefault)
- format = typedef_clang_type.GetFormat();
- clang::TypeInfo typedef_type_info = getASTContext()->getTypeInfo(typedef_qual_type);
- uint64_t typedef_byte_size = typedef_type_info.Width / 8;
-
- return typedef_clang_type.DumpTypeValue (s,
- format, // The format with which to display the element
- data, // Data buffer containing all bytes for this type
- byte_offset, // Offset into "data" where to grab value from
- typedef_byte_size, // Size of this type in bytes
- bitfield_bit_size, // Size in bits of a bitfield value, if zero don't treat as a bitfield
- bitfield_bit_offset, // Offset in bits of a bitfield value if bitfield_bit_size != 0
- exe_scope);
- }
- break;
-
- case clang::Type::Enum:
- // If our format is enum or default, show the enumeration value as
- // its enumeration string value, else just display it as requested.
- if ((format == eFormatEnum || format == eFormatDefault) && GetCompleteType(type))
- {
- const clang::EnumType *enutype = llvm::cast<clang::EnumType>(qual_type.getTypePtr());
- const clang::EnumDecl *enum_decl = enutype->getDecl();
- assert(enum_decl);
- clang::EnumDecl::enumerator_iterator enum_pos, enum_end_pos;
- const bool is_signed = qual_type->isSignedIntegerOrEnumerationType();
- lldb::offset_t offset = byte_offset;
- if (is_signed)
- {
- const int64_t enum_svalue = data.GetMaxS64Bitfield (&offset, byte_size, bitfield_bit_size, bitfield_bit_offset);
- for (enum_pos = enum_decl->enumerator_begin(), enum_end_pos = enum_decl->enumerator_end(); enum_pos != enum_end_pos; ++enum_pos)
- {
- if (enum_pos->getInitVal().getSExtValue() == enum_svalue)
- {
- s->PutCString (enum_pos->getNameAsString().c_str());
- return true;
- }
- }
- // If we have gotten here we didn't get find the enumerator in the
- // enum decl, so just print the integer.
- s->Printf("%" PRIi64, enum_svalue);
- }
- else
- {
- const uint64_t enum_uvalue = data.GetMaxU64Bitfield (&offset, byte_size, bitfield_bit_size, bitfield_bit_offset);
- for (enum_pos = enum_decl->enumerator_begin(), enum_end_pos = enum_decl->enumerator_end(); enum_pos != enum_end_pos; ++enum_pos)
- {
- if (enum_pos->getInitVal().getZExtValue() == enum_uvalue)
- {
- s->PutCString (enum_pos->getNameAsString().c_str());
- return true;
- }
- }
- // If we have gotten here we didn't get find the enumerator in the
- // enum decl, so just print the integer.
- s->Printf("%" PRIu64, enum_uvalue);
- }
- return true;
- }
- // format was not enum, just fall through and dump the value as requested....
- LLVM_FALLTHROUGH;
-
- default:
- // We are down to a scalar type that we just need to display.
- {
- uint32_t item_count = 1;
- // A few formats, we might need to modify our size and count for depending
- // on how we are trying to display the value...
- switch (format)
- {
- default:
- case eFormatBoolean:
- case eFormatBinary:
- case eFormatComplex:
- case eFormatCString: // NULL terminated C strings
- case eFormatDecimal:
- case eFormatEnum:
- case eFormatHex:
- case eFormatHexUppercase:
- case eFormatFloat:
- case eFormatOctal:
- case eFormatOSType:
- case eFormatUnsigned:
- case eFormatPointer:
- case eFormatVectorOfChar:
- case eFormatVectorOfSInt8:
- case eFormatVectorOfUInt8:
- case eFormatVectorOfSInt16:
- case eFormatVectorOfUInt16:
- case eFormatVectorOfSInt32:
- case eFormatVectorOfUInt32:
- case eFormatVectorOfSInt64:
- case eFormatVectorOfUInt64:
- case eFormatVectorOfFloat32:
- case eFormatVectorOfFloat64:
- case eFormatVectorOfUInt128:
- break;
-
- case eFormatChar:
- case eFormatCharPrintable:
- case eFormatCharArray:
- case eFormatBytes:
- case eFormatBytesWithASCII:
- item_count = byte_size;
- byte_size = 1;
- break;
-
- case eFormatUnicode16:
- item_count = byte_size / 2;
- byte_size = 2;
- break;
-
- case eFormatUnicode32:
- item_count = byte_size / 4;
- byte_size = 4;
- break;
- }
- return data.Dump (s,
- byte_offset,
- format,
- byte_size,
- item_count,
- UINT32_MAX,
- LLDB_INVALID_ADDRESS,
- bitfield_bit_size,
- bitfield_bit_offset,
- exe_scope);
- }
- break;
- }
- }
- return 0;
+void ClangASTContext::DumpTypeDescription(lldb::opaque_compiler_type_t type) {
+ StreamFile s(stdout, false);
+ DumpTypeDescription(type, &s);
+ ClangASTMetadata *metadata =
+ ClangASTContext::GetMetadata(getASTContext(), type);
+ if (metadata) {
+ metadata->Dump(&s);
+ }
}
+void ClangASTContext::DumpTypeDescription(lldb::opaque_compiler_type_t type,
+ Stream *s) {
+ if (type) {
+ clang::QualType qual_type(GetQualType(type));
+ llvm::SmallVector<char, 1024> buf;
+ llvm::raw_svector_ostream llvm_ostrm(buf);
-void
-ClangASTContext::DumpSummary (lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx,
- Stream *s,
- const lldb_private::DataExtractor &data,
- lldb::offset_t data_byte_offset,
- size_t data_byte_size)
-{
- uint32_t length = 0;
- if (IsCStringType (type, length))
- {
- if (exe_ctx)
- {
- Process *process = exe_ctx->GetProcessPtr();
- if (process)
- {
- lldb::offset_t offset = data_byte_offset;
- lldb::addr_t pointer_address = data.GetMaxU64(&offset, data_byte_size);
- std::vector<uint8_t> buf;
- if (length > 0)
- buf.resize (length);
- else
- buf.resize (256);
-
- lldb_private::DataExtractor cstr_data(&buf.front(), buf.size(), process->GetByteOrder(), 4);
- buf.back() = '\0';
- size_t bytes_read;
- size_t total_cstr_len = 0;
- Error error;
- while ((bytes_read = process->ReadMemory (pointer_address, &buf.front(), buf.size(), error)) > 0)
- {
- const size_t len = strlen((const char *)&buf.front());
- if (len == 0)
- break;
- if (total_cstr_len == 0)
- s->PutCString (" \"");
- cstr_data.Dump(s, 0, lldb::eFormatChar, 1, len, UINT32_MAX, LLDB_INVALID_ADDRESS, 0, 0);
- total_cstr_len += len;
- if (len < buf.size())
- break;
- pointer_address += total_cstr_len;
- }
- if (total_cstr_len > 0)
- s->PutChar ('"');
- }
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::ObjCObject:
+ case clang::Type::ObjCInterface: {
+ GetCompleteType(type);
+
+ const clang::ObjCObjectType *objc_class_type =
+ llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
+ assert(objc_class_type);
+ if (objc_class_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterface();
+ if (class_interface_decl) {
+ clang::PrintingPolicy policy = getASTContext()->getPrintingPolicy();
+ class_interface_decl->print(llvm_ostrm, policy, s->GetIndentLevel());
+ }
+ }
+ } break;
+
+ case clang::Type::Typedef: {
+ const clang::TypedefType *typedef_type =
+ qual_type->getAs<clang::TypedefType>();
+ if (typedef_type) {
+ const clang::TypedefNameDecl *typedef_decl = typedef_type->getDecl();
+ std::string clang_typedef_name(
+ typedef_decl->getQualifiedNameAsString());
+ if (!clang_typedef_name.empty()) {
+ s->PutCString("typedef ");
+ s->PutCString(clang_typedef_name.c_str());
}
+ }
+ } break;
+
+ case clang::Type::Auto:
+ CompilerType(getASTContext(),
+ llvm::cast<clang::AutoType>(qual_type)->getDeducedType())
+ .DumpTypeDescription(s);
+ return;
+
+ case clang::Type::Elaborated:
+ CompilerType(getASTContext(),
+ llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType())
+ .DumpTypeDescription(s);
+ return;
+
+ case clang::Type::Paren:
+ CompilerType(getASTContext(),
+ llvm::cast<clang::ParenType>(qual_type)->desugar())
+ .DumpTypeDescription(s);
+ return;
+
+ case clang::Type::Record: {
+ GetCompleteType(type);
+
+ const clang::RecordType *record_type =
+ llvm::cast<clang::RecordType>(qual_type.getTypePtr());
+ const clang::RecordDecl *record_decl = record_type->getDecl();
+ const clang::CXXRecordDecl *cxx_record_decl =
+ llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
+
+ if (cxx_record_decl)
+ cxx_record_decl->print(llvm_ostrm, getASTContext()->getPrintingPolicy(),
+ s->GetIndentLevel());
+ else
+ record_decl->print(llvm_ostrm, getASTContext()->getPrintingPolicy(),
+ s->GetIndentLevel());
+ } break;
+
+ default: {
+ const clang::TagType *tag_type =
+ llvm::dyn_cast<clang::TagType>(qual_type.getTypePtr());
+ if (tag_type) {
+ clang::TagDecl *tag_decl = tag_type->getDecl();
+ if (tag_decl)
+ tag_decl->print(llvm_ostrm, 0);
+ } else {
+ std::string clang_type_name(qual_type.getAsString());
+ if (!clang_type_name.empty())
+ s->PutCString(clang_type_name.c_str());
+ }
}
-}
-
-void
-ClangASTContext::DumpTypeDescription (lldb::opaque_compiler_type_t type)
-{
- StreamFile s (stdout, false);
- DumpTypeDescription (type, &s);
- ClangASTMetadata *metadata = ClangASTContext::GetMetadata (getASTContext(), type);
- if (metadata)
- {
- metadata->Dump (&s);
}
-}
-void
-ClangASTContext::DumpTypeDescription (lldb::opaque_compiler_type_t type, Stream *s)
-{
- if (type)
- {
- clang::QualType qual_type(GetQualType(type));
-
- llvm::SmallVector<char, 1024> buf;
- llvm::raw_svector_ostream llvm_ostrm (buf);
-
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::ObjCObject:
- case clang::Type::ObjCInterface:
- {
- GetCompleteType(type);
-
- const clang::ObjCObjectType *objc_class_type = llvm::dyn_cast<clang::ObjCObjectType>(qual_type.getTypePtr());
- assert (objc_class_type);
- if (objc_class_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
- if (class_interface_decl)
- {
- clang::PrintingPolicy policy = getASTContext()->getPrintingPolicy();
- class_interface_decl->print(llvm_ostrm, policy, s->GetIndentLevel());
- }
- }
- }
- break;
-
- case clang::Type::Typedef:
- {
- const clang::TypedefType *typedef_type = qual_type->getAs<clang::TypedefType>();
- if (typedef_type)
- {
- const clang::TypedefNameDecl *typedef_decl = typedef_type->getDecl();
- std::string clang_typedef_name (typedef_decl->getQualifiedNameAsString());
- if (!clang_typedef_name.empty())
- {
- s->PutCString ("typedef ");
- s->PutCString (clang_typedef_name.c_str());
- }
- }
- }
- break;
-
- case clang::Type::Auto:
- CompilerType (getASTContext(), llvm::cast<clang::AutoType>(qual_type)->getDeducedType()).DumpTypeDescription(s);
- return;
-
- case clang::Type::Elaborated:
- CompilerType (getASTContext(), llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType()).DumpTypeDescription(s);
- return;
-
- case clang::Type::Paren:
- CompilerType (getASTContext(), llvm::cast<clang::ParenType>(qual_type)->desugar()).DumpTypeDescription(s);
- return;
-
- case clang::Type::Record:
- {
- GetCompleteType(type);
-
- const clang::RecordType *record_type = llvm::cast<clang::RecordType>(qual_type.getTypePtr());
- const clang::RecordDecl *record_decl = record_type->getDecl();
- const clang::CXXRecordDecl *cxx_record_decl = llvm::dyn_cast<clang::CXXRecordDecl>(record_decl);
-
- if (cxx_record_decl)
- cxx_record_decl->print(llvm_ostrm, getASTContext()->getPrintingPolicy(), s->GetIndentLevel());
- else
- record_decl->print(llvm_ostrm, getASTContext()->getPrintingPolicy(), s->GetIndentLevel());
- }
- break;
-
- default:
- {
- const clang::TagType *tag_type = llvm::dyn_cast<clang::TagType>(qual_type.getTypePtr());
- if (tag_type)
- {
- clang::TagDecl *tag_decl = tag_type->getDecl();
- if (tag_decl)
- tag_decl->print(llvm_ostrm, 0);
- }
- else
- {
- std::string clang_type_name(qual_type.getAsString());
- if (!clang_type_name.empty())
- s->PutCString (clang_type_name.c_str());
- }
- }
- }
-
- if (buf.size() > 0)
- {
- s->Write (buf.data(), buf.size());
- }
+ if (buf.size() > 0) {
+ s->Write(buf.data(), buf.size());
}
+ }
}
-void
-ClangASTContext::DumpTypeName (const CompilerType &type)
-{
- if (ClangUtil::IsClangType(type))
- {
- clang::QualType qual_type(ClangUtil::GetCanonicalQualType(ClangUtil::RemoveFastQualifiers(type)));
-
- const clang::Type::TypeClass type_class = qual_type->getTypeClass();
- switch (type_class)
- {
- case clang::Type::Record:
- {
- const clang::CXXRecordDecl *cxx_record_decl = qual_type->getAsCXXRecordDecl();
- if (cxx_record_decl)
- printf("class %s", cxx_record_decl->getName().str().c_str());
- }
- break;
-
- case clang::Type::Enum:
- {
- clang::EnumDecl *enum_decl = llvm::cast<clang::EnumType>(qual_type)->getDecl();
- if (enum_decl)
- {
- printf("enum %s", enum_decl->getName().str().c_str());
- }
- }
- break;
-
- case clang::Type::ObjCObject:
- case clang::Type::ObjCInterface:
- {
- const clang::ObjCObjectType *objc_class_type = llvm::dyn_cast<clang::ObjCObjectType>(qual_type);
- if (objc_class_type)
- {
- clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface();
- // We currently can't complete objective C types through the newly added ASTContext
- // because it only supports TagDecl objects right now...
- if (class_interface_decl)
- printf("@class %s", class_interface_decl->getName().str().c_str());
- }
- }
- break;
+void ClangASTContext::DumpTypeName(const CompilerType &type) {
+ if (ClangUtil::IsClangType(type)) {
+ clang::QualType qual_type(
+ ClangUtil::GetCanonicalQualType(ClangUtil::RemoveFastQualifiers(type)));
+ const clang::Type::TypeClass type_class = qual_type->getTypeClass();
+ switch (type_class) {
+ case clang::Type::Record: {
+ const clang::CXXRecordDecl *cxx_record_decl =
+ qual_type->getAsCXXRecordDecl();
+ if (cxx_record_decl)
+ printf("class %s", cxx_record_decl->getName().str().c_str());
+ } break;
+
+ case clang::Type::Enum: {
+ clang::EnumDecl *enum_decl =
+ llvm::cast<clang::EnumType>(qual_type)->getDecl();
+ if (enum_decl) {
+ printf("enum %s", enum_decl->getName().str().c_str());
+ }
+ } break;
+
+ case clang::Type::ObjCObject:
+ case clang::Type::ObjCInterface: {
+ const clang::ObjCObjectType *objc_class_type =
+ llvm::dyn_cast<clang::ObjCObjectType>(qual_type);
+ if (objc_class_type) {
+ clang::ObjCInterfaceDecl *class_interface_decl =
+ objc_class_type->getInterface();
+ // We currently can't complete objective C types through the newly added
+ // ASTContext
+ // because it only supports TagDecl objects right now...
+ if (class_interface_decl)
+ printf("@class %s", class_interface_decl->getName().str().c_str());
+ }
+ } break;
+
+ case clang::Type::Typedef:
+ printf("typedef %s", llvm::cast<clang::TypedefType>(qual_type)
+ ->getDecl()
+ ->getName()
+ .str()
+ .c_str());
+ break;
+
+ case clang::Type::Auto:
+ printf("auto ");
+ return DumpTypeName(CompilerType(type.GetTypeSystem(),
+ llvm::cast<clang::AutoType>(qual_type)
+ ->getDeducedType()
+ .getAsOpaquePtr()));
+
+ case clang::Type::Elaborated:
+ printf("elaborated ");
+ return DumpTypeName(CompilerType(
+ type.GetTypeSystem(), llvm::cast<clang::ElaboratedType>(qual_type)
+ ->getNamedType()
+ .getAsOpaquePtr()));
+
+ case clang::Type::Paren:
+ printf("paren ");
+ return DumpTypeName(CompilerType(
+ type.GetTypeSystem(),
+ llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr()));
- case clang::Type::Typedef:
- printf("typedef %s", llvm::cast<clang::TypedefType>(qual_type)->getDecl()->getName().str().c_str());
- break;
-
- case clang::Type::Auto:
- printf("auto ");
- return DumpTypeName (CompilerType (type.GetTypeSystem(), llvm::cast<clang::AutoType>(qual_type)->getDeducedType().getAsOpaquePtr()));
-
- case clang::Type::Elaborated:
- printf("elaborated ");
- return DumpTypeName (CompilerType (type.GetTypeSystem(), llvm::cast<clang::ElaboratedType>(qual_type)->getNamedType().getAsOpaquePtr()));
-
- case clang::Type::Paren:
- printf("paren ");
- return DumpTypeName (CompilerType (type.GetTypeSystem(), llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr()));
-
- default:
- printf("ClangASTContext::DumpTypeName() type_class = %u", type_class);
- break;
- }
+ default:
+ printf("ClangASTContext::DumpTypeName() type_class = %u", type_class);
+ break;
}
-
+ }
}
+clang::ClassTemplateDecl *ClangASTContext::ParseClassTemplateDecl(
+ clang::DeclContext *decl_ctx, lldb::AccessType access_type,
+ const char *parent_name, int tag_decl_kind,
+ const ClangASTContext::TemplateParameterInfos &template_param_infos) {
+ if (template_param_infos.IsValid()) {
+ std::string template_basename(parent_name);
+ template_basename.erase(template_basename.find('<'));
-
-clang::ClassTemplateDecl *
-ClangASTContext::ParseClassTemplateDecl (clang::DeclContext *decl_ctx,
- lldb::AccessType access_type,
- const char *parent_name,
- int tag_decl_kind,
- const ClangASTContext::TemplateParameterInfos &template_param_infos)
-{
- if (template_param_infos.IsValid())
- {
- std::string template_basename(parent_name);
- template_basename.erase (template_basename.find('<'));
-
- return CreateClassTemplateDecl (decl_ctx,
- access_type,
- template_basename.c_str(),
- tag_decl_kind,
- template_param_infos);
- }
- return NULL;
+ return CreateClassTemplateDecl(decl_ctx, access_type,
+ template_basename.c_str(), tag_decl_kind,
+ template_param_infos);
+ }
+ return NULL;
}
-void
-ClangASTContext::CompleteTagDecl (void *baton, clang::TagDecl *decl)
-{
- ClangASTContext *ast = (ClangASTContext *)baton;
- SymbolFile *sym_file = ast->GetSymbolFile();
- if (sym_file)
- {
- CompilerType clang_type = GetTypeForDecl (decl);
- if (clang_type)
- sym_file->CompleteType (clang_type);
- }
+void ClangASTContext::CompleteTagDecl(void *baton, clang::TagDecl *decl) {
+ ClangASTContext *ast = (ClangASTContext *)baton;
+ SymbolFile *sym_file = ast->GetSymbolFile();
+ if (sym_file) {
+ CompilerType clang_type = GetTypeForDecl(decl);
+ if (clang_type)
+ sym_file->CompleteType(clang_type);
+ }
}
-void
-ClangASTContext::CompleteObjCInterfaceDecl (void *baton, clang::ObjCInterfaceDecl *decl)
-{
- ClangASTContext *ast = (ClangASTContext *)baton;
- SymbolFile *sym_file = ast->GetSymbolFile();
- if (sym_file)
- {
- CompilerType clang_type = GetTypeForDecl (decl);
- if (clang_type)
- sym_file->CompleteType (clang_type);
- }
+void ClangASTContext::CompleteObjCInterfaceDecl(
+ void *baton, clang::ObjCInterfaceDecl *decl) {
+ ClangASTContext *ast = (ClangASTContext *)baton;
+ SymbolFile *sym_file = ast->GetSymbolFile();
+ if (sym_file) {
+ CompilerType clang_type = GetTypeForDecl(decl);
+ if (clang_type)
+ sym_file->CompleteType(clang_type);
+ }
}
-DWARFASTParser *
-ClangASTContext::GetDWARFParser()
-{
- if (!m_dwarf_ast_parser_ap)
- m_dwarf_ast_parser_ap.reset(new DWARFASTParserClang(*this));
- return m_dwarf_ast_parser_ap.get();
+DWARFASTParser *ClangASTContext::GetDWARFParser() {
+ if (!m_dwarf_ast_parser_ap)
+ m_dwarf_ast_parser_ap.reset(new DWARFASTParserClang(*this));
+ return m_dwarf_ast_parser_ap.get();
}
-PDBASTParser *
-ClangASTContext::GetPDBParser()
-{
- if (!m_pdb_ast_parser_ap)
- m_pdb_ast_parser_ap.reset(new PDBASTParser(*this));
- return m_pdb_ast_parser_ap.get();
+PDBASTParser *ClangASTContext::GetPDBParser() {
+ if (!m_pdb_ast_parser_ap)
+ m_pdb_ast_parser_ap.reset(new PDBASTParser(*this));
+ return m_pdb_ast_parser_ap.get();
}
-bool
-ClangASTContext::LayoutRecordType(void *baton,
- const clang::RecordDecl *record_decl,
- uint64_t &bit_size,
- uint64_t &alignment,
- llvm::DenseMap<const clang::FieldDecl *, uint64_t> &field_offsets,
- llvm::DenseMap<const clang::CXXRecordDecl *, clang::CharUnits> &base_offsets,
- llvm::DenseMap<const clang::CXXRecordDecl *, clang::CharUnits> &vbase_offsets)
-{
- ClangASTContext *ast = (ClangASTContext *)baton;
- DWARFASTParserClang *dwarf_ast_parser = (DWARFASTParserClang *)ast->GetDWARFParser();
- return dwarf_ast_parser->GetClangASTImporter().LayoutRecordType(record_decl, bit_size, alignment, field_offsets,
- base_offsets, vbase_offsets);
+bool ClangASTContext::LayoutRecordType(
+ void *baton, const clang::RecordDecl *record_decl, uint64_t &bit_size,
+ uint64_t &alignment,
+ llvm::DenseMap<const clang::FieldDecl *, uint64_t> &field_offsets,
+ llvm::DenseMap<const clang::CXXRecordDecl *, clang::CharUnits>
+ &base_offsets,
+ llvm::DenseMap<const clang::CXXRecordDecl *, clang::CharUnits>
+ &vbase_offsets) {
+ ClangASTContext *ast = (ClangASTContext *)baton;
+ DWARFASTParserClang *dwarf_ast_parser =
+ (DWARFASTParserClang *)ast->GetDWARFParser();
+ return dwarf_ast_parser->GetClangASTImporter().LayoutRecordType(
+ record_decl, bit_size, alignment, field_offsets, base_offsets,
+ vbase_offsets);
}
//----------------------------------------------------------------------
// CompilerDecl override functions
//----------------------------------------------------------------------
-ConstString
-ClangASTContext::DeclGetName (void *opaque_decl)
-{
- if (opaque_decl)
- {
- clang::NamedDecl *nd = llvm::dyn_cast<NamedDecl>((clang::Decl*)opaque_decl);
- if (nd != nullptr)
- return ConstString(nd->getDeclName().getAsString());
- }
- return ConstString();
-}
-
-ConstString
-ClangASTContext::DeclGetMangledName (void *opaque_decl)
-{
- if (opaque_decl)
- {
- clang::NamedDecl *nd = llvm::dyn_cast<clang::NamedDecl>((clang::Decl*)opaque_decl);
- if (nd != nullptr && !llvm::isa<clang::ObjCMethodDecl>(nd))
- {
- clang::MangleContext *mc = getMangleContext();
- if (mc && mc->shouldMangleCXXName(nd))
- {
- llvm::SmallVector<char, 1024> buf;
- llvm::raw_svector_ostream llvm_ostrm (buf);
- if (llvm::isa<clang::CXXConstructorDecl>(nd))
- {
- mc->mangleCXXCtor(llvm::dyn_cast<clang::CXXConstructorDecl>(nd), Ctor_Complete, llvm_ostrm);
- }
- else if (llvm::isa<clang::CXXDestructorDecl>(nd))
- {
- mc->mangleCXXDtor(llvm::dyn_cast<clang::CXXDestructorDecl>(nd), Dtor_Complete, llvm_ostrm);
- }
- else
- {
- mc->mangleName(nd, llvm_ostrm);
- }
- if (buf.size() > 0)
- return ConstString(buf.data(), buf.size());
- }
+ConstString ClangASTContext::DeclGetName(void *opaque_decl) {
+ if (opaque_decl) {
+ clang::NamedDecl *nd =
+ llvm::dyn_cast<NamedDecl>((clang::Decl *)opaque_decl);
+ if (nd != nullptr)
+ return ConstString(nd->getDeclName().getAsString());
+ }
+ return ConstString();
+}
+
+ConstString ClangASTContext::DeclGetMangledName(void *opaque_decl) {
+ if (opaque_decl) {
+ clang::NamedDecl *nd =
+ llvm::dyn_cast<clang::NamedDecl>((clang::Decl *)opaque_decl);
+ if (nd != nullptr && !llvm::isa<clang::ObjCMethodDecl>(nd)) {
+ clang::MangleContext *mc = getMangleContext();
+ if (mc && mc->shouldMangleCXXName(nd)) {
+ llvm::SmallVector<char, 1024> buf;
+ llvm::raw_svector_ostream llvm_ostrm(buf);
+ if (llvm::isa<clang::CXXConstructorDecl>(nd)) {
+ mc->mangleCXXCtor(llvm::dyn_cast<clang::CXXConstructorDecl>(nd),
+ Ctor_Complete, llvm_ostrm);
+ } else if (llvm::isa<clang::CXXDestructorDecl>(nd)) {
+ mc->mangleCXXDtor(llvm::dyn_cast<clang::CXXDestructorDecl>(nd),
+ Dtor_Complete, llvm_ostrm);
+ } else {
+ mc->mangleName(nd, llvm_ostrm);
}
+ if (buf.size() > 0)
+ return ConstString(buf.data(), buf.size());
+ }
}
- return ConstString();
+ }
+ return ConstString();
}
-CompilerDeclContext
-ClangASTContext::DeclGetDeclContext (void *opaque_decl)
-{
- if (opaque_decl)
- return CompilerDeclContext(this, ((clang::Decl*)opaque_decl)->getDeclContext());
- else
- return CompilerDeclContext();
+CompilerDeclContext ClangASTContext::DeclGetDeclContext(void *opaque_decl) {
+ if (opaque_decl)
+ return CompilerDeclContext(this,
+ ((clang::Decl *)opaque_decl)->getDeclContext());
+ else
+ return CompilerDeclContext();
}
-CompilerType
-ClangASTContext::DeclGetFunctionReturnType(void *opaque_decl)
-{
- if (clang::FunctionDecl *func_decl = llvm::dyn_cast<clang::FunctionDecl>((clang::Decl*)opaque_decl))
- return CompilerType(this, func_decl->getReturnType().getAsOpaquePtr());
- if (clang::ObjCMethodDecl *objc_method = llvm::dyn_cast<clang::ObjCMethodDecl>((clang::Decl*)opaque_decl))
- return CompilerType(this, objc_method->getReturnType().getAsOpaquePtr());
- else
- return CompilerType();
+CompilerType ClangASTContext::DeclGetFunctionReturnType(void *opaque_decl) {
+ if (clang::FunctionDecl *func_decl =
+ llvm::dyn_cast<clang::FunctionDecl>((clang::Decl *)opaque_decl))
+ return CompilerType(this, func_decl->getReturnType().getAsOpaquePtr());
+ if (clang::ObjCMethodDecl *objc_method =
+ llvm::dyn_cast<clang::ObjCMethodDecl>((clang::Decl *)opaque_decl))
+ return CompilerType(this, objc_method->getReturnType().getAsOpaquePtr());
+ else
+ return CompilerType();
}
-size_t
-ClangASTContext::DeclGetFunctionNumArguments(void *opaque_decl)
-{
- if (clang::FunctionDecl *func_decl = llvm::dyn_cast<clang::FunctionDecl>((clang::Decl*)opaque_decl))
- return func_decl->param_size();
- if (clang::ObjCMethodDecl *objc_method = llvm::dyn_cast<clang::ObjCMethodDecl>((clang::Decl*)opaque_decl))
- return objc_method->param_size();
- else
- return 0;
+size_t ClangASTContext::DeclGetFunctionNumArguments(void *opaque_decl) {
+ if (clang::FunctionDecl *func_decl =
+ llvm::dyn_cast<clang::FunctionDecl>((clang::Decl *)opaque_decl))
+ return func_decl->param_size();
+ if (clang::ObjCMethodDecl *objc_method =
+ llvm::dyn_cast<clang::ObjCMethodDecl>((clang::Decl *)opaque_decl))
+ return objc_method->param_size();
+ else
+ return 0;
}
-CompilerType
-ClangASTContext::DeclGetFunctionArgumentType (void *opaque_decl, size_t idx)
-{
- if (clang::FunctionDecl *func_decl = llvm::dyn_cast<clang::FunctionDecl>((clang::Decl*)opaque_decl))
- {
- if (idx < func_decl->param_size())
- {
- ParmVarDecl *var_decl = func_decl->getParamDecl(idx);
- if (var_decl)
- return CompilerType(this, var_decl->getOriginalType().getAsOpaquePtr());
- }
- }
- else if (clang::ObjCMethodDecl *objc_method = llvm::dyn_cast<clang::ObjCMethodDecl>((clang::Decl*)opaque_decl))
- {
- if (idx < objc_method->param_size())
- return CompilerType(this, objc_method->parameters()[idx]->getOriginalType().getAsOpaquePtr());
+CompilerType ClangASTContext::DeclGetFunctionArgumentType(void *opaque_decl,
+ size_t idx) {
+ if (clang::FunctionDecl *func_decl =
+ llvm::dyn_cast<clang::FunctionDecl>((clang::Decl *)opaque_decl)) {
+ if (idx < func_decl->param_size()) {
+ ParmVarDecl *var_decl = func_decl->getParamDecl(idx);
+ if (var_decl)
+ return CompilerType(this, var_decl->getOriginalType().getAsOpaquePtr());
}
- return CompilerType();
+ } else if (clang::ObjCMethodDecl *objc_method =
+ llvm::dyn_cast<clang::ObjCMethodDecl>(
+ (clang::Decl *)opaque_decl)) {
+ if (idx < objc_method->param_size())
+ return CompilerType(
+ this,
+ objc_method->parameters()[idx]->getOriginalType().getAsOpaquePtr());
+ }
+ return CompilerType();
}
//----------------------------------------------------------------------
// CompilerDeclContext functions
//----------------------------------------------------------------------
-std::vector<CompilerDecl>
-ClangASTContext::DeclContextFindDeclByName(void *opaque_decl_ctx,
- ConstString name,
- const bool ignore_using_decls)
-{
- std::vector<CompilerDecl> found_decls;
- if (opaque_decl_ctx)
- {
- DeclContext *root_decl_ctx = (DeclContext *)opaque_decl_ctx;
- std::set<DeclContext *> searched;
- std::multimap<DeclContext *, DeclContext *> search_queue;
- SymbolFile *symbol_file = GetSymbolFile();
-
- for (clang::DeclContext *decl_context = root_decl_ctx; decl_context != nullptr && found_decls.empty(); decl_context = decl_context->getParent())
- {
- search_queue.insert(std::make_pair(decl_context, decl_context));
-
- for (auto it = search_queue.find(decl_context); it != search_queue.end(); it++)
- {
- if (!searched.insert(it->second).second)
- continue;
- symbol_file->ParseDeclsForContext(CompilerDeclContext(this, it->second));
-
- for (clang::Decl *child : it->second->decls())
- {
- if (clang::UsingDirectiveDecl *ud = llvm::dyn_cast<clang::UsingDirectiveDecl>(child))
- {
- if (ignore_using_decls)
- continue;
- clang::DeclContext *from = ud->getCommonAncestor();
- if (searched.find(ud->getNominatedNamespace()) == searched.end())
- search_queue.insert(std::make_pair(from, ud->getNominatedNamespace()));
- }
- else if (clang::UsingDecl *ud = llvm::dyn_cast<clang::UsingDecl>(child))
- {
- if (ignore_using_decls)
- continue;
- for (clang::UsingShadowDecl *usd : ud->shadows())
- {
- clang::Decl *target = usd->getTargetDecl();
- if (clang::NamedDecl *nd = llvm::dyn_cast<clang::NamedDecl>(target))
- {
- IdentifierInfo *ii = nd->getIdentifier();
- if (ii != nullptr && ii->getName().equals(name.AsCString(nullptr)))
- found_decls.push_back(CompilerDecl(this, nd));
- }
- }
- }
- else if (clang::NamedDecl *nd = llvm::dyn_cast<clang::NamedDecl>(child))
- {
- IdentifierInfo *ii = nd->getIdentifier();
- if (ii != nullptr && ii->getName().equals(name.AsCString(nullptr)))
- found_decls.push_back(CompilerDecl(this, nd));
- }
- }
+std::vector<CompilerDecl> ClangASTContext::DeclContextFindDeclByName(
+ void *opaque_decl_ctx, ConstString name, const bool ignore_using_decls) {
+ std::vector<CompilerDecl> found_decls;
+ if (opaque_decl_ctx) {
+ DeclContext *root_decl_ctx = (DeclContext *)opaque_decl_ctx;
+ std::set<DeclContext *> searched;
+ std::multimap<DeclContext *, DeclContext *> search_queue;
+ SymbolFile *symbol_file = GetSymbolFile();
+
+ for (clang::DeclContext *decl_context = root_decl_ctx;
+ decl_context != nullptr && found_decls.empty();
+ decl_context = decl_context->getParent()) {
+ search_queue.insert(std::make_pair(decl_context, decl_context));
+
+ for (auto it = search_queue.find(decl_context); it != search_queue.end();
+ it++) {
+ if (!searched.insert(it->second).second)
+ continue;
+ symbol_file->ParseDeclsForContext(
+ CompilerDeclContext(this, it->second));
+
+ for (clang::Decl *child : it->second->decls()) {
+ if (clang::UsingDirectiveDecl *ud =
+ llvm::dyn_cast<clang::UsingDirectiveDecl>(child)) {
+ if (ignore_using_decls)
+ continue;
+ clang::DeclContext *from = ud->getCommonAncestor();
+ if (searched.find(ud->getNominatedNamespace()) == searched.end())
+ search_queue.insert(
+ std::make_pair(from, ud->getNominatedNamespace()));
+ } else if (clang::UsingDecl *ud =
+ llvm::dyn_cast<clang::UsingDecl>(child)) {
+ if (ignore_using_decls)
+ continue;
+ for (clang::UsingShadowDecl *usd : ud->shadows()) {
+ clang::Decl *target = usd->getTargetDecl();
+ if (clang::NamedDecl *nd =
+ llvm::dyn_cast<clang::NamedDecl>(target)) {
+ IdentifierInfo *ii = nd->getIdentifier();
+ if (ii != nullptr &&
+ ii->getName().equals(name.AsCString(nullptr)))
+ found_decls.push_back(CompilerDecl(this, nd));
+ }
}
+ } else if (clang::NamedDecl *nd =
+ llvm::dyn_cast<clang::NamedDecl>(child)) {
+ IdentifierInfo *ii = nd->getIdentifier();
+ if (ii != nullptr && ii->getName().equals(name.AsCString(nullptr)))
+ found_decls.push_back(CompilerDecl(this, nd));
+ }
}
+ }
}
- return found_decls;
+ }
+ return found_decls;
}
// Look for child_decl_ctx's lookup scope in frame_decl_ctx and its parents,
-// and return the number of levels it took to find it, or LLDB_INVALID_DECL_LEVEL
-// if not found. If the decl was imported via a using declaration, its name and/or
-// type, if set, will be used to check that the decl found in the scope is a match.
+// and return the number of levels it took to find it, or
+// LLDB_INVALID_DECL_LEVEL
+// if not found. If the decl was imported via a using declaration, its name
+// and/or
+// type, if set, will be used to check that the decl found in the scope is a
+// match.
//
-// The optional name is required by languages (like C++) to handle using declarations
+// The optional name is required by languages (like C++) to handle using
+// declarations
// like:
//
// void poo();
@@ -9927,288 +9804,269 @@ ClangASTContext::DeclContextFindDeclByName(void *opaque_decl_ctx,
// }
//
// NOTE: Because file statics are at the TranslationUnit along with globals, a
-// function at file scope will return the same level as a function at global scope.
-// Ideally we'd like to treat the file scope as an additional scope just below the
-// global scope. More work needs to be done to recognise that, if the decl we're
-// trying to look up is static, we should compare its source file with that of the
+// function at file scope will return the same level as a function at global
+// scope.
+// Ideally we'd like to treat the file scope as an additional scope just below
+// the
+// global scope. More work needs to be done to recognise that, if the decl
+// we're
+// trying to look up is static, we should compare its source file with that of
+// the
// current scope and return a lower number for it.
-uint32_t
-ClangASTContext::CountDeclLevels (clang::DeclContext *frame_decl_ctx,
- clang::DeclContext *child_decl_ctx,
- ConstString *child_name,
- CompilerType *child_type)
-{
- if (frame_decl_ctx)
- {
- std::set<DeclContext *> searched;
- std::multimap<DeclContext *, DeclContext *> search_queue;
- SymbolFile *symbol_file = GetSymbolFile();
-
- // Get the lookup scope for the decl we're trying to find.
- clang::DeclContext *parent_decl_ctx = child_decl_ctx->getParent();
-
- // Look for it in our scope's decl context and its parents.
- uint32_t level = 0;
- for (clang::DeclContext *decl_ctx = frame_decl_ctx; decl_ctx != nullptr; decl_ctx = decl_ctx->getParent())
- {
- if (!decl_ctx->isLookupContext())
- continue;
- if (decl_ctx == parent_decl_ctx)
- // Found it!
- return level;
- search_queue.insert(std::make_pair(decl_ctx, decl_ctx));
- for (auto it = search_queue.find(decl_ctx); it != search_queue.end(); it++)
- {
- if (searched.find(it->second) != searched.end())
+uint32_t ClangASTContext::CountDeclLevels(clang::DeclContext *frame_decl_ctx,
+ clang::DeclContext *child_decl_ctx,
+ ConstString *child_name,
+ CompilerType *child_type) {
+ if (frame_decl_ctx) {
+ std::set<DeclContext *> searched;
+ std::multimap<DeclContext *, DeclContext *> search_queue;
+ SymbolFile *symbol_file = GetSymbolFile();
+
+ // Get the lookup scope for the decl we're trying to find.
+ clang::DeclContext *parent_decl_ctx = child_decl_ctx->getParent();
+
+ // Look for it in our scope's decl context and its parents.
+ uint32_t level = 0;
+ for (clang::DeclContext *decl_ctx = frame_decl_ctx; decl_ctx != nullptr;
+ decl_ctx = decl_ctx->getParent()) {
+ if (!decl_ctx->isLookupContext())
+ continue;
+ if (decl_ctx == parent_decl_ctx)
+ // Found it!
+ return level;
+ search_queue.insert(std::make_pair(decl_ctx, decl_ctx));
+ for (auto it = search_queue.find(decl_ctx); it != search_queue.end();
+ it++) {
+ if (searched.find(it->second) != searched.end())
+ continue;
+
+ // Currently DWARF has one shared translation unit for all Decls at top
+ // level, so this
+ // would erroneously find using statements anywhere. So don't look at
+ // the top-level
+ // translation unit.
+ // TODO fix this and add a testcase that depends on it.
+
+ if (llvm::isa<clang::TranslationUnitDecl>(it->second))
+ continue;
+
+ searched.insert(it->second);
+ symbol_file->ParseDeclsForContext(
+ CompilerDeclContext(this, it->second));
+
+ for (clang::Decl *child : it->second->decls()) {
+ if (clang::UsingDirectiveDecl *ud =
+ llvm::dyn_cast<clang::UsingDirectiveDecl>(child)) {
+ clang::DeclContext *ns = ud->getNominatedNamespace();
+ if (ns == parent_decl_ctx)
+ // Found it!
+ return level;
+ clang::DeclContext *from = ud->getCommonAncestor();
+ if (searched.find(ns) == searched.end())
+ search_queue.insert(std::make_pair(from, ns));
+ } else if (child_name) {
+ if (clang::UsingDecl *ud =
+ llvm::dyn_cast<clang::UsingDecl>(child)) {
+ for (clang::UsingShadowDecl *usd : ud->shadows()) {
+ clang::Decl *target = usd->getTargetDecl();
+ clang::NamedDecl *nd = llvm::dyn_cast<clang::NamedDecl>(target);
+ if (!nd)
+ continue;
+ // Check names.
+ IdentifierInfo *ii = nd->getIdentifier();
+ if (ii == nullptr ||
+ !ii->getName().equals(child_name->AsCString(nullptr)))
+ continue;
+ // Check types, if one was provided.
+ if (child_type) {
+ CompilerType clang_type = ClangASTContext::GetTypeForDecl(nd);
+ if (!AreTypesSame(clang_type, *child_type,
+ /*ignore_qualifiers=*/true))
continue;
-
- // Currently DWARF has one shared translation unit for all Decls at top level, so this
- // would erroneously find using statements anywhere. So don't look at the top-level
- // translation unit.
- // TODO fix this and add a testcase that depends on it.
-
- if (llvm::isa<clang::TranslationUnitDecl>(it->second))
- continue;
-
- searched.insert(it->second);
- symbol_file->ParseDeclsForContext(CompilerDeclContext(this, it->second));
-
- for (clang::Decl *child : it->second->decls())
- {
- if (clang::UsingDirectiveDecl *ud = llvm::dyn_cast<clang::UsingDirectiveDecl>(child))
- {
- clang::DeclContext *ns = ud->getNominatedNamespace();
- if (ns == parent_decl_ctx)
- // Found it!
- return level;
- clang::DeclContext *from = ud->getCommonAncestor();
- if (searched.find(ns) == searched.end())
- search_queue.insert(std::make_pair(from, ns));
- }
- else if (child_name)
- {
- if (clang::UsingDecl *ud = llvm::dyn_cast<clang::UsingDecl>(child))
- {
- for (clang::UsingShadowDecl *usd : ud->shadows())
- {
- clang::Decl *target = usd->getTargetDecl();
- clang::NamedDecl *nd = llvm::dyn_cast<clang::NamedDecl>(target);
- if (!nd)
- continue;
- // Check names.
- IdentifierInfo *ii = nd->getIdentifier();
- if (ii == nullptr || !ii->getName().equals(child_name->AsCString(nullptr)))
- continue;
- // Check types, if one was provided.
- if (child_type)
- {
- CompilerType clang_type = ClangASTContext::GetTypeForDecl(nd);
- if (!AreTypesSame(clang_type, *child_type, /*ignore_qualifiers=*/true))
- continue;
- }
- // Found it!
- return level;
- }
- }
- }
}
+ // Found it!
+ return level;
+ }
}
- ++level;
+ }
}
+ }
+ ++level;
}
- return LLDB_INVALID_DECL_LEVEL;
+ }
+ return LLDB_INVALID_DECL_LEVEL;
}
-bool
-ClangASTContext::DeclContextIsStructUnionOrClass (void *opaque_decl_ctx)
-{
- if (opaque_decl_ctx)
- return ((clang::DeclContext *)opaque_decl_ctx)->isRecord();
- else
- return false;
+bool ClangASTContext::DeclContextIsStructUnionOrClass(void *opaque_decl_ctx) {
+ if (opaque_decl_ctx)
+ return ((clang::DeclContext *)opaque_decl_ctx)->isRecord();
+ else
+ return false;
}
-ConstString
-ClangASTContext::DeclContextGetName (void *opaque_decl_ctx)
-{
- if (opaque_decl_ctx)
- {
- clang::NamedDecl *named_decl = llvm::dyn_cast<clang::NamedDecl>((clang::DeclContext *)opaque_decl_ctx);
- if (named_decl)
- return ConstString(named_decl->getName());
- }
- return ConstString();
+ConstString ClangASTContext::DeclContextGetName(void *opaque_decl_ctx) {
+ if (opaque_decl_ctx) {
+ clang::NamedDecl *named_decl =
+ llvm::dyn_cast<clang::NamedDecl>((clang::DeclContext *)opaque_decl_ctx);
+ if (named_decl)
+ return ConstString(named_decl->getName());
+ }
+ return ConstString();
}
ConstString
-ClangASTContext::DeclContextGetScopeQualifiedName (void *opaque_decl_ctx)
-{
- if (opaque_decl_ctx)
- {
- clang::NamedDecl *named_decl = llvm::dyn_cast<clang::NamedDecl>((clang::DeclContext *)opaque_decl_ctx);
- if (named_decl)
- return ConstString(llvm::StringRef(named_decl->getQualifiedNameAsString()));
- }
- return ConstString();
-}
-
-bool
-ClangASTContext::DeclContextIsClassMethod (void *opaque_decl_ctx,
- lldb::LanguageType *language_ptr,
- bool *is_instance_method_ptr,
- ConstString *language_object_name_ptr)
-{
- if (opaque_decl_ctx)
- {
- clang::DeclContext *decl_ctx = (clang::DeclContext *)opaque_decl_ctx;
- if (ObjCMethodDecl *objc_method = llvm::dyn_cast<clang::ObjCMethodDecl>(decl_ctx))
- {
- if (is_instance_method_ptr)
- *is_instance_method_ptr = objc_method->isInstanceMethod();
- if (language_ptr)
- *language_ptr = eLanguageTypeObjC;
- if (language_object_name_ptr)
- language_object_name_ptr->SetCString("self");
- return true;
- }
- else if (CXXMethodDecl *cxx_method = llvm::dyn_cast<clang::CXXMethodDecl>(decl_ctx))
- {
- if (is_instance_method_ptr)
- *is_instance_method_ptr = cxx_method->isInstance();
- if (language_ptr)
- *language_ptr = eLanguageTypeC_plus_plus;
- if (language_object_name_ptr)
- language_object_name_ptr->SetCString("this");
- return true;
- }
- else if (clang::FunctionDecl *function_decl = llvm::dyn_cast<clang::FunctionDecl>(decl_ctx))
- {
- ClangASTMetadata *metadata = GetMetadata (&decl_ctx->getParentASTContext(), function_decl);
- if (metadata && metadata->HasObjectPtr())
- {
- if (is_instance_method_ptr)
- *is_instance_method_ptr = true;
- if (language_ptr)
- *language_ptr = eLanguageTypeObjC;
- if (language_object_name_ptr)
- language_object_name_ptr->SetCString (metadata->GetObjectPtrName());
- return true;
- }
- }
+ClangASTContext::DeclContextGetScopeQualifiedName(void *opaque_decl_ctx) {
+ if (opaque_decl_ctx) {
+ clang::NamedDecl *named_decl =
+ llvm::dyn_cast<clang::NamedDecl>((clang::DeclContext *)opaque_decl_ctx);
+ if (named_decl)
+ return ConstString(
+ llvm::StringRef(named_decl->getQualifiedNameAsString()));
+ }
+ return ConstString();
+}
+
+bool ClangASTContext::DeclContextIsClassMethod(
+ void *opaque_decl_ctx, lldb::LanguageType *language_ptr,
+ bool *is_instance_method_ptr, ConstString *language_object_name_ptr) {
+ if (opaque_decl_ctx) {
+ clang::DeclContext *decl_ctx = (clang::DeclContext *)opaque_decl_ctx;
+ if (ObjCMethodDecl *objc_method =
+ llvm::dyn_cast<clang::ObjCMethodDecl>(decl_ctx)) {
+ if (is_instance_method_ptr)
+ *is_instance_method_ptr = objc_method->isInstanceMethod();
+ if (language_ptr)
+ *language_ptr = eLanguageTypeObjC;
+ if (language_object_name_ptr)
+ language_object_name_ptr->SetCString("self");
+ return true;
+ } else if (CXXMethodDecl *cxx_method =
+ llvm::dyn_cast<clang::CXXMethodDecl>(decl_ctx)) {
+ if (is_instance_method_ptr)
+ *is_instance_method_ptr = cxx_method->isInstance();
+ if (language_ptr)
+ *language_ptr = eLanguageTypeC_plus_plus;
+ if (language_object_name_ptr)
+ language_object_name_ptr->SetCString("this");
+ return true;
+ } else if (clang::FunctionDecl *function_decl =
+ llvm::dyn_cast<clang::FunctionDecl>(decl_ctx)) {
+ ClangASTMetadata *metadata =
+ GetMetadata(&decl_ctx->getParentASTContext(), function_decl);
+ if (metadata && metadata->HasObjectPtr()) {
+ if (is_instance_method_ptr)
+ *is_instance_method_ptr = true;
+ if (language_ptr)
+ *language_ptr = eLanguageTypeObjC;
+ if (language_object_name_ptr)
+ language_object_name_ptr->SetCString(metadata->GetObjectPtrName());
+ return true;
+ }
}
- return false;
+ }
+ return false;
}
clang::DeclContext *
-ClangASTContext::DeclContextGetAsDeclContext (const CompilerDeclContext &dc)
-{
- if (dc.IsClang())
- return (clang::DeclContext *)dc.GetOpaqueDeclContext();
- return nullptr;
+ClangASTContext::DeclContextGetAsDeclContext(const CompilerDeclContext &dc) {
+ if (dc.IsClang())
+ return (clang::DeclContext *)dc.GetOpaqueDeclContext();
+ return nullptr;
}
-
ObjCMethodDecl *
-ClangASTContext::DeclContextGetAsObjCMethodDecl (const CompilerDeclContext &dc)
-{
- if (dc.IsClang())
- return llvm::dyn_cast<clang::ObjCMethodDecl>((clang::DeclContext *)dc.GetOpaqueDeclContext());
- return nullptr;
+ClangASTContext::DeclContextGetAsObjCMethodDecl(const CompilerDeclContext &dc) {
+ if (dc.IsClang())
+ return llvm::dyn_cast<clang::ObjCMethodDecl>(
+ (clang::DeclContext *)dc.GetOpaqueDeclContext());
+ return nullptr;
}
CXXMethodDecl *
-ClangASTContext::DeclContextGetAsCXXMethodDecl (const CompilerDeclContext &dc)
-{
- if (dc.IsClang())
- return llvm::dyn_cast<clang::CXXMethodDecl>((clang::DeclContext *)dc.GetOpaqueDeclContext());
- return nullptr;
+ClangASTContext::DeclContextGetAsCXXMethodDecl(const CompilerDeclContext &dc) {
+ if (dc.IsClang())
+ return llvm::dyn_cast<clang::CXXMethodDecl>(
+ (clang::DeclContext *)dc.GetOpaqueDeclContext());
+ return nullptr;
}
clang::FunctionDecl *
-ClangASTContext::DeclContextGetAsFunctionDecl (const CompilerDeclContext &dc)
-{
- if (dc.IsClang())
- return llvm::dyn_cast<clang::FunctionDecl>((clang::DeclContext *)dc.GetOpaqueDeclContext());
- return nullptr;
+ClangASTContext::DeclContextGetAsFunctionDecl(const CompilerDeclContext &dc) {
+ if (dc.IsClang())
+ return llvm::dyn_cast<clang::FunctionDecl>(
+ (clang::DeclContext *)dc.GetOpaqueDeclContext());
+ return nullptr;
}
clang::NamespaceDecl *
-ClangASTContext::DeclContextGetAsNamespaceDecl (const CompilerDeclContext &dc)
-{
- if (dc.IsClang())
- return llvm::dyn_cast<clang::NamespaceDecl>((clang::DeclContext *)dc.GetOpaqueDeclContext());
- return nullptr;
+ClangASTContext::DeclContextGetAsNamespaceDecl(const CompilerDeclContext &dc) {
+ if (dc.IsClang())
+ return llvm::dyn_cast<clang::NamespaceDecl>(
+ (clang::DeclContext *)dc.GetOpaqueDeclContext());
+ return nullptr;
}
ClangASTMetadata *
-ClangASTContext::DeclContextGetMetaData (const CompilerDeclContext &dc, const void *object)
-{
- clang::ASTContext *ast = DeclContextGetClangASTContext (dc);
- if (ast)
- return ClangASTContext::GetMetadata (ast, object);
- return nullptr;
+ClangASTContext::DeclContextGetMetaData(const CompilerDeclContext &dc,
+ const void *object) {
+ clang::ASTContext *ast = DeclContextGetClangASTContext(dc);
+ if (ast)
+ return ClangASTContext::GetMetadata(ast, object);
+ return nullptr;
}
clang::ASTContext *
-ClangASTContext::DeclContextGetClangASTContext (const CompilerDeclContext &dc)
-{
- ClangASTContext *ast = llvm::dyn_cast_or_null<ClangASTContext>(dc.GetTypeSystem());
- if (ast)
- return ast->getASTContext();
+ClangASTContext::DeclContextGetClangASTContext(const CompilerDeclContext &dc) {
+ ClangASTContext *ast =
+ llvm::dyn_cast_or_null<ClangASTContext>(dc.GetTypeSystem());
+ if (ast)
+ return ast->getASTContext();
+ return nullptr;
+}
+
+ClangASTContextForExpressions::ClangASTContextForExpressions(Target &target)
+ : ClangASTContext(target.GetArchitecture().GetTriple().getTriple().c_str()),
+ m_target_wp(target.shared_from_this()),
+ m_persistent_variables(new ClangPersistentVariables) {}
+
+UserExpression *ClangASTContextForExpressions::GetUserExpression(
+ const char *expr, const char *expr_prefix, lldb::LanguageType language,
+ Expression::ResultType desired_type,
+ const EvaluateExpressionOptions &options) {
+ TargetSP target_sp = m_target_wp.lock();
+ if (!target_sp)
return nullptr;
+
+ return new ClangUserExpression(*target_sp.get(), expr, expr_prefix, language,
+ desired_type, options);
}
-ClangASTContextForExpressions::ClangASTContextForExpressions (Target &target) :
- ClangASTContext (target.GetArchitecture().GetTriple().getTriple().c_str()),
- m_target_wp(target.shared_from_this()),
- m_persistent_variables (new ClangPersistentVariables)
-{
-}
-
-UserExpression *
-ClangASTContextForExpressions::GetUserExpression (const char *expr,
- const char *expr_prefix,
- lldb::LanguageType language,
- Expression::ResultType desired_type,
- const EvaluateExpressionOptions &options)
-{
- TargetSP target_sp = m_target_wp.lock();
- if (!target_sp)
- return nullptr;
-
- return new ClangUserExpression(*target_sp.get(), expr, expr_prefix, language, desired_type, options);
-}
-
-FunctionCaller *
-ClangASTContextForExpressions::GetFunctionCaller (const CompilerType &return_type,
- const Address& function_address,
- const ValueList &arg_value_list,
- const char *name)
-{
- TargetSP target_sp = m_target_wp.lock();
- if (!target_sp)
- return nullptr;
-
- Process *process = target_sp->GetProcessSP().get();
- if (!process)
- return nullptr;
-
- return new ClangFunctionCaller (*process, return_type, function_address, arg_value_list, name);
+FunctionCaller *ClangASTContextForExpressions::GetFunctionCaller(
+ const CompilerType &return_type, const Address &function_address,
+ const ValueList &arg_value_list, const char *name) {
+ TargetSP target_sp = m_target_wp.lock();
+ if (!target_sp)
+ return nullptr;
+
+ Process *process = target_sp->GetProcessSP().get();
+ if (!process)
+ return nullptr;
+
+ return new ClangFunctionCaller(*process, return_type, function_address,
+ arg_value_list, name);
}
UtilityFunction *
-ClangASTContextForExpressions::GetUtilityFunction (const char *text,
- const char *name)
-{
- TargetSP target_sp = m_target_wp.lock();
- if (!target_sp)
- return nullptr;
-
- return new ClangUtilityFunction(*target_sp.get(), text, name);
+ClangASTContextForExpressions::GetUtilityFunction(const char *text,
+ const char *name) {
+ TargetSP target_sp = m_target_wp.lock();
+ if (!target_sp)
+ return nullptr;
+
+ return new ClangUtilityFunction(*target_sp.get(), text, name);
}
PersistentExpressionState *
-ClangASTContextForExpressions::GetPersistentExpressionState ()
-{
- return m_persistent_variables.get();
+ClangASTContextForExpressions::GetPersistentExpressionState() {
+ return m_persistent_variables.get();
}