[Lldb-commits] [lldb] r265200 - Add some unit tests for ClangASTContext.
Zachary Turner via lldb-commits
lldb-commits at lists.llvm.org
Fri Apr 1 16:20:36 PDT 2016
Author: zturner
Date: Fri Apr 1 18:20:35 2016
New Revision: 265200
URL: http://llvm.org/viewvc/llvm-project?rev=265200&view=rev
Log:
Add some unit tests for ClangASTContext.
In doing so, two bugs were uncovered (and fixed). The first bug
is that ClangASTContext::RemoveFastQualifiers() was broken, and
was not removing fast qualifiers (or doing anything else for that
matter). The second bug is that UnifyAccessSpecifiers treated
AS_None asymmetrically, which is probably an edge case, but seems
like a bug nonetheless.
Added:
lldb/trunk/unittests/Symbol/
lldb/trunk/unittests/Symbol/CMakeLists.txt
lldb/trunk/unittests/Symbol/TestClangASTContext.cpp
Modified:
lldb/trunk/include/lldb/Symbol/ClangASTContext.h
lldb/trunk/source/Symbol/ClangASTContext.cpp
lldb/trunk/source/Symbol/ClangUtil.cpp
lldb/trunk/unittests/CMakeLists.txt
Modified: lldb/trunk/include/lldb/Symbol/ClangASTContext.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Symbol/ClangASTContext.h?rev=265200&r1=265199&r2=265200&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Symbol/ClangASTContext.h (original)
+++ lldb/trunk/include/lldb/Symbol/ClangASTContext.h Fri Apr 1 18:20:35 2016
@@ -1151,23 +1151,26 @@ public:
clang::VarDecl *
CreateVariableDeclaration (clang::DeclContext *decl_context, const char *name, clang::QualType type);
-protected:
+ static lldb::opaque_compiler_type_t
+ GetOpaqueCompilerType(clang::ASTContext *ast, lldb::BasicType basic_type);
+
static clang::QualType
- GetQualType (lldb::opaque_compiler_type_t type)
+ GetQualType(lldb::opaque_compiler_type_t type)
{
if (type)
return clang::QualType::getFromOpaquePtr(type);
return clang::QualType();
}
-
+
static clang::QualType
- GetCanonicalQualType (lldb::opaque_compiler_type_t type)
+ GetCanonicalQualType(lldb::opaque_compiler_type_t type)
{
if (type)
return clang::QualType::getFromOpaquePtr(type).getCanonicalType();
return clang::QualType();
}
+protected:
//------------------------------------------------------------------
// Classes that inherit from ClangASTContext can see and modify these
//------------------------------------------------------------------
Modified: lldb/trunk/source/Symbol/ClangASTContext.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/ClangASTContext.cpp?rev=265200&r1=265199&r2=265200&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/ClangASTContext.cpp (original)
+++ lldb/trunk/source/Symbol/ClangASTContext.cpp Fri Apr 1 18:20:35 2016
@@ -911,113 +911,12 @@ ClangASTContext::GetBasicType (lldb::Bas
CompilerType
ClangASTContext::GetBasicType (ASTContext *ast, lldb::BasicType basic_type)
{
- if (ast)
- {
- lldb::opaque_compiler_type_t clang_type = nullptr;
-
- switch (basic_type)
- {
- case eBasicTypeInvalid:
- case eBasicTypeOther:
- break;
- case eBasicTypeVoid:
- clang_type = ast->VoidTy.getAsOpaquePtr();
- break;
- case eBasicTypeChar:
- clang_type = ast->CharTy.getAsOpaquePtr();
- break;
- case eBasicTypeSignedChar:
- clang_type = ast->SignedCharTy.getAsOpaquePtr();
- break;
- case eBasicTypeUnsignedChar:
- clang_type = ast->UnsignedCharTy.getAsOpaquePtr();
- break;
- case eBasicTypeWChar:
- clang_type = ast->getWCharType().getAsOpaquePtr();
- break;
- case eBasicTypeSignedWChar:
- clang_type = ast->getSignedWCharType().getAsOpaquePtr();
- break;
- case eBasicTypeUnsignedWChar:
- clang_type = ast->getUnsignedWCharType().getAsOpaquePtr();
- break;
- case eBasicTypeChar16:
- clang_type = ast->Char16Ty.getAsOpaquePtr();
- break;
- case eBasicTypeChar32:
- clang_type = ast->Char32Ty.getAsOpaquePtr();
- break;
- case eBasicTypeShort:
- clang_type = ast->ShortTy.getAsOpaquePtr();
- break;
- case eBasicTypeUnsignedShort:
- clang_type = ast->UnsignedShortTy.getAsOpaquePtr();
- break;
- case eBasicTypeInt:
- clang_type = ast->IntTy.getAsOpaquePtr();
- break;
- case eBasicTypeUnsignedInt:
- clang_type = ast->UnsignedIntTy.getAsOpaquePtr();
- break;
- case eBasicTypeLong:
- clang_type = ast->LongTy.getAsOpaquePtr();
- break;
- case eBasicTypeUnsignedLong:
- clang_type = ast->UnsignedLongTy.getAsOpaquePtr();
- break;
- case eBasicTypeLongLong:
- clang_type = ast->LongLongTy.getAsOpaquePtr();
- break;
- case eBasicTypeUnsignedLongLong:
- clang_type = ast->UnsignedLongLongTy.getAsOpaquePtr();
- break;
- case eBasicTypeInt128:
- clang_type = ast->Int128Ty.getAsOpaquePtr();
- break;
- case eBasicTypeUnsignedInt128:
- clang_type = ast->UnsignedInt128Ty.getAsOpaquePtr();
- break;
- case eBasicTypeBool:
- clang_type = ast->BoolTy.getAsOpaquePtr();
- break;
- case eBasicTypeHalf:
- clang_type = ast->HalfTy.getAsOpaquePtr();
- break;
- case eBasicTypeFloat:
- clang_type = ast->FloatTy.getAsOpaquePtr();
- break;
- case eBasicTypeDouble:
- clang_type = ast->DoubleTy.getAsOpaquePtr();
- break;
- case eBasicTypeLongDouble:
- clang_type = ast->LongDoubleTy.getAsOpaquePtr();
- break;
- case eBasicTypeFloatComplex:
- clang_type = ast->FloatComplexTy.getAsOpaquePtr();
- break;
- case eBasicTypeDoubleComplex:
- clang_type = ast->DoubleComplexTy.getAsOpaquePtr();
- break;
- case eBasicTypeLongDoubleComplex:
- clang_type = ast->LongDoubleComplexTy.getAsOpaquePtr();
- break;
- case eBasicTypeObjCID:
- clang_type = ast->getObjCIdType().getAsOpaquePtr();
- break;
- case eBasicTypeObjCClass:
- clang_type = ast->getObjCClassType().getAsOpaquePtr();
- break;
- case eBasicTypeObjCSel:
- clang_type = ast->getObjCSelType().getAsOpaquePtr();
- break;
- case eBasicTypeNullPtr:
- clang_type = ast->NullPtrTy.getAsOpaquePtr();
- break;
- }
-
- if (clang_type)
- return CompilerType (GetASTContext(ast), clang_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();
}
@@ -1662,25 +1561,14 @@ ClangASTContext::CheckOverloadedOperator
clang::AccessSpecifier
ClangASTContext::UnifyAccessSpecifiers (clang::AccessSpecifier lhs, clang::AccessSpecifier rhs)
{
- clang::AccessSpecifier ret = lhs;
-
// Make the access equal to the stricter of the field and the nested field's access
- switch (ret)
- {
- case clang::AS_none:
- break;
- case clang::AS_private:
- break;
- case clang::AS_protected:
- if (rhs == AS_private)
- ret = AS_private;
- break;
- case clang::AS_public:
- ret = rhs;
- break;
- }
-
- return ret;
+ 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
@@ -1998,6 +1886,78 @@ ClangASTContext::CreateVariableDeclarati
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;
+ }
+}
+
#pragma mark Function Types
FunctionDecl *
@@ -5824,7 +5784,8 @@ ClangASTContext::GetVirtualBaseClassAtIn
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);
+ return GetVirtualBaseClassAtIndex(llvm::cast<clang::ParenType>(qual_type)->desugar().getAsOpaquePtr(), idx,
+ bit_offset_ptr);
default:
break;
@@ -9583,7 +9544,7 @@ ClangASTContext::DeclGetFunctionNumArgum
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();
+ return objc_method->param_size();
else
return 0;
}
@@ -9597,7 +9558,7 @@ ClangASTContext::DeclGetFunctionArgument
{
ParmVarDecl *var_decl = func_decl->getParamDecl(idx);
if (var_decl)
- return CompilerType(this, var_decl->getOriginalType().getAsOpaquePtr());
+ return CompilerType(this, var_decl->getOriginalType().getAsOpaquePtr());
}
}
else if (clang::ObjCMethodDecl *objc_method = llvm::dyn_cast<clang::ObjCMethodDecl>((clang::Decl*)opaque_decl))
Modified: lldb/trunk/source/Symbol/ClangUtil.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/ClangUtil.cpp?rev=265200&r1=265199&r2=265200&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/ClangUtil.cpp (original)
+++ lldb/trunk/source/Symbol/ClangUtil.cpp Fri Apr 1 18:20:35 2016
@@ -53,6 +53,6 @@ ClangUtil::RemoveFastQualifiers(const Co
return ct;
QualType qual_type(GetQualType(ct));
- qual_type.getQualifiers().removeFastQualifiers();
+ qual_type.removeLocalFastQualifiers();
return CompilerType(ct.GetTypeSystem(), qual_type.getAsOpaquePtr());
}
Modified: lldb/trunk/unittests/CMakeLists.txt
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/unittests/CMakeLists.txt?rev=265200&r1=265199&r2=265200&view=diff
==============================================================================
--- lldb/trunk/unittests/CMakeLists.txt (original)
+++ lldb/trunk/unittests/CMakeLists.txt Fri Apr 1 18:20:35 2016
@@ -44,5 +44,6 @@ add_subdirectory(Expression)
add_subdirectory(Host)
add_subdirectory(Interpreter)
add_subdirectory(ScriptInterpreter)
+add_subdirectory(Symbol)
add_subdirectory(SymbolFile)
add_subdirectory(Utility)
Added: lldb/trunk/unittests/Symbol/CMakeLists.txt
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/unittests/Symbol/CMakeLists.txt?rev=265200&view=auto
==============================================================================
--- lldb/trunk/unittests/Symbol/CMakeLists.txt (added)
+++ lldb/trunk/unittests/Symbol/CMakeLists.txt Fri Apr 1 18:20:35 2016
@@ -0,0 +1,3 @@
+add_lldb_unittest(SymbolTests
+ TestClangASTContext.cpp
+ )
Added: lldb/trunk/unittests/Symbol/TestClangASTContext.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/unittests/Symbol/TestClangASTContext.cpp?rev=265200&view=auto
==============================================================================
--- lldb/trunk/unittests/Symbol/TestClangASTContext.cpp (added)
+++ lldb/trunk/unittests/Symbol/TestClangASTContext.cpp Fri Apr 1 18:20:35 2016
@@ -0,0 +1,315 @@
+//===-- TestClangASTContext.cpp ---------------------------------------*- C++ -*-===//
+
+//
+// The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#include "gtest/gtest.h"
+
+#include "lldb/Host/HostInfo.h"
+#include "lldb/Symbol/ClangASTContext.h"
+#include "lldb/Symbol/ClangUtil.h"
+#include "lldb/Symbol/Declaration.h"
+#include "lldb/Symbol/GoASTContext.h"
+
+using namespace clang;
+using namespace lldb;
+using namespace lldb_private;
+
+class TestClangASTContext : public testing::Test
+{
+public:
+ static void
+ SetUpTestCase()
+ {
+ HostInfo::Initialize();
+ }
+
+ static void
+ TearDownTestCase()
+ {
+ HostInfo::Terminate();
+ }
+
+ virtual void
+ SetUp() override
+ {
+ std::string triple = HostInfo::GetTargetTriple();
+ m_ast.reset(new ClangASTContext(triple.c_str()));
+ }
+
+ virtual void
+ TearDown() override
+ {
+ m_ast.reset();
+ }
+
+protected:
+ std::unique_ptr<ClangASTContext> m_ast;
+
+ QualType
+ GetBasicQualType(BasicType type) const
+ {
+ return ClangUtil::GetQualType(m_ast->GetBasicTypeFromAST(type));
+ }
+
+ QualType
+ GetBasicQualType(const char *name) const
+ {
+ return ClangUtil::GetQualType(m_ast->GetBuiltinTypeByName(ConstString(name)));
+ }
+};
+
+TEST_F(TestClangASTContext, TestGetBasicTypeFromEnum)
+{
+ clang::ASTContext *context = m_ast->getASTContext();
+
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeBool), context->BoolTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeChar), context->CharTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeChar16), context->Char16Ty));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeChar32), context->Char32Ty));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeDouble), context->DoubleTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeDoubleComplex), context->DoubleComplexTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeFloat), context->FloatTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeFloatComplex), context->FloatComplexTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeHalf), context->HalfTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeInt), context->IntTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeInt128), context->Int128Ty));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeLong), context->LongTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeLongDouble), context->LongDoubleTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeLongDoubleComplex), context->LongDoubleComplexTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeLongLong), context->LongLongTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeNullPtr), context->NullPtrTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeObjCClass), context->getObjCClassType()));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeObjCID), context->getObjCIdType()));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeObjCSel), context->getObjCSelType()));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeShort), context->ShortTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeSignedChar), context->SignedCharTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeUnsignedChar), context->UnsignedCharTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeUnsignedInt), context->UnsignedIntTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeUnsignedInt128), context->UnsignedInt128Ty));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeUnsignedLong), context->UnsignedLongTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeUnsignedLongLong), context->UnsignedLongLongTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeUnsignedShort), context->UnsignedShortTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeVoid), context->VoidTy));
+ EXPECT_TRUE(context->hasSameType(GetBasicQualType(eBasicTypeWChar), context->WCharTy));
+}
+
+TEST_F(TestClangASTContext, TestGetBasicTypeFromName)
+{
+ EXPECT_EQ(GetBasicQualType(eBasicTypeChar), GetBasicQualType("char"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeSignedChar), GetBasicQualType("signed char"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeUnsignedChar), GetBasicQualType("unsigned char"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeWChar), GetBasicQualType("wchar_t"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeSignedWChar), GetBasicQualType("signed wchar_t"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeUnsignedWChar), GetBasicQualType("unsigned wchar_t"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeShort), GetBasicQualType("short"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeShort), GetBasicQualType("short int"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeUnsignedShort), GetBasicQualType("unsigned short"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeUnsignedShort), GetBasicQualType("unsigned short int"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeInt), GetBasicQualType("int"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeInt), GetBasicQualType("signed int"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeUnsignedInt), GetBasicQualType("unsigned int"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeUnsignedInt), GetBasicQualType("unsigned"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeLong), GetBasicQualType("long"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeLong), GetBasicQualType("long int"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeUnsignedLong), GetBasicQualType("unsigned long"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeUnsignedLong), GetBasicQualType("unsigned long int"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeLongLong), GetBasicQualType("long long"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeLongLong), GetBasicQualType("long long int"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeUnsignedLongLong), GetBasicQualType("unsigned long long"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeUnsignedLongLong), GetBasicQualType("unsigned long long int"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeInt128), GetBasicQualType("__int128_t"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeUnsignedInt128), GetBasicQualType("__uint128_t"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeVoid), GetBasicQualType("void"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeBool), GetBasicQualType("bool"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeFloat), GetBasicQualType("float"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeDouble), GetBasicQualType("double"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeLongDouble), GetBasicQualType("long double"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeObjCID), GetBasicQualType("id"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeObjCSel), GetBasicQualType("SEL"));
+ EXPECT_EQ(GetBasicQualType(eBasicTypeNullPtr), GetBasicQualType("nullptr"));
+}
+
+void
+VerifyEncodingAndBitSize(clang::ASTContext *context, lldb::Encoding encoding, int bit_size)
+{
+ CompilerType type = ClangASTContext::GetBuiltinTypeForEncodingAndBitSize(context, encoding, bit_size);
+ EXPECT_TRUE(type.IsValid());
+
+ QualType qtype = ClangUtil::GetQualType(type);
+ EXPECT_FALSE(qtype.isNull());
+ if (qtype.isNull())
+ return;
+
+ uint64_t actual_size = context->getTypeSize(qtype);
+ EXPECT_EQ(bit_size, actual_size);
+
+ const clang::Type *type_ptr = qtype.getTypePtr();
+ EXPECT_NE(nullptr, type_ptr);
+ if (!type_ptr)
+ return;
+
+ EXPECT_TRUE(type_ptr->isBuiltinType());
+ if (encoding == eEncodingSint)
+ EXPECT_TRUE(type_ptr->isSignedIntegerType());
+ else if (encoding == eEncodingUint)
+ EXPECT_TRUE(type_ptr->isUnsignedIntegerType());
+ else if (encoding == eEncodingIEEE754)
+ EXPECT_TRUE(type_ptr->isFloatingType());
+}
+
+TEST_F(TestClangASTContext, TestBuiltinTypeForEncodingAndBitSize)
+{
+ clang::ASTContext *context = m_ast->getASTContext();
+
+ // Make sure we can get types of every possible size in every possible encoding.
+ // We can't make any guarantee about which specific type we get, because the standard
+ // isn't that specific. We only need to make sure the compiler hands us some type that
+ // is both a builtin type and matches the requested bit size.
+ VerifyEncodingAndBitSize(context, eEncodingSint, 8);
+ VerifyEncodingAndBitSize(context, eEncodingSint, 16);
+ VerifyEncodingAndBitSize(context, eEncodingSint, 32);
+ VerifyEncodingAndBitSize(context, eEncodingSint, 64);
+ VerifyEncodingAndBitSize(context, eEncodingSint, 128);
+
+ VerifyEncodingAndBitSize(context, eEncodingUint, 8);
+ VerifyEncodingAndBitSize(context, eEncodingUint, 16);
+ VerifyEncodingAndBitSize(context, eEncodingUint, 32);
+ VerifyEncodingAndBitSize(context, eEncodingUint, 64);
+ VerifyEncodingAndBitSize(context, eEncodingUint, 128);
+
+ VerifyEncodingAndBitSize(context, eEncodingIEEE754, 32);
+ VerifyEncodingAndBitSize(context, eEncodingIEEE754, 64);
+}
+
+TEST_F(TestClangASTContext, TestIsClangType)
+{
+ clang::ASTContext *context = m_ast->getASTContext();
+ lldb::opaque_compiler_type_t bool_ctype = ClangASTContext::GetOpaqueCompilerType(context, lldb::eBasicTypeBool);
+ CompilerType bool_type(m_ast.get(), bool_ctype);
+ CompilerType record_type = m_ast->CreateRecordType(nullptr, lldb::eAccessPublic, "FooRecord", clang::TTK_Struct,
+ lldb::eLanguageTypeC_plus_plus, nullptr);
+ // Clang builtin type and record type should pass
+ EXPECT_TRUE(ClangUtil::IsClangType(bool_type));
+ EXPECT_TRUE(ClangUtil::IsClangType(record_type));
+
+ // Default constructed type should fail
+ EXPECT_FALSE(ClangUtil::IsClangType(CompilerType()));
+
+ // Go type should fail
+ GoASTContext go_ast;
+ CompilerType go_type(&go_ast, bool_ctype);
+ EXPECT_FALSE(ClangUtil::IsClangType(go_type));
+}
+
+TEST_F(TestClangASTContext, TestRemoveFastQualifiers)
+{
+ CompilerType record_type = m_ast->CreateRecordType(nullptr, lldb::eAccessPublic, "FooRecord", clang::TTK_Struct,
+ lldb::eLanguageTypeC_plus_plus, nullptr);
+ QualType qt;
+
+ qt = ClangUtil::GetQualType(record_type);
+ EXPECT_EQ(0, qt.getLocalFastQualifiers());
+ record_type = record_type.AddConstModifier();
+ record_type = record_type.AddVolatileModifier();
+ record_type = record_type.AddRestrictModifier();
+ qt = ClangUtil::GetQualType(record_type);
+ EXPECT_NE(0, qt.getLocalFastQualifiers());
+ record_type = ClangUtil::RemoveFastQualifiers(record_type);
+ qt = ClangUtil::GetQualType(record_type);
+ EXPECT_EQ(0, qt.getLocalFastQualifiers());
+}
+
+TEST_F(TestClangASTContext, TestConvertAccessTypeToAccessSpecifier)
+{
+ EXPECT_EQ(AS_none, ClangASTContext::ConvertAccessTypeToAccessSpecifier(eAccessNone));
+ EXPECT_EQ(AS_none, ClangASTContext::ConvertAccessTypeToAccessSpecifier(eAccessPackage));
+ EXPECT_EQ(AS_public, ClangASTContext::ConvertAccessTypeToAccessSpecifier(eAccessPublic));
+ EXPECT_EQ(AS_private, ClangASTContext::ConvertAccessTypeToAccessSpecifier(eAccessPrivate));
+ EXPECT_EQ(AS_protected, ClangASTContext::ConvertAccessTypeToAccessSpecifier(eAccessProtected));
+}
+
+TEST_F(TestClangASTContext, TestUnifyAccessSpecifiers)
+{
+ // Unifying two of the same type should return the same type
+ EXPECT_EQ(AS_public, ClangASTContext::UnifyAccessSpecifiers(AS_public, AS_public));
+ EXPECT_EQ(AS_private, ClangASTContext::UnifyAccessSpecifiers(AS_private, AS_private));
+ EXPECT_EQ(AS_protected, ClangASTContext::UnifyAccessSpecifiers(AS_protected, AS_protected));
+
+ // Otherwise the result should be the strictest of the two.
+ EXPECT_EQ(AS_private, ClangASTContext::UnifyAccessSpecifiers(AS_private, AS_public));
+ EXPECT_EQ(AS_private, ClangASTContext::UnifyAccessSpecifiers(AS_private, AS_protected));
+ EXPECT_EQ(AS_private, ClangASTContext::UnifyAccessSpecifiers(AS_public, AS_private));
+ EXPECT_EQ(AS_private, ClangASTContext::UnifyAccessSpecifiers(AS_protected, AS_private));
+ EXPECT_EQ(AS_protected, ClangASTContext::UnifyAccessSpecifiers(AS_protected, AS_public));
+ EXPECT_EQ(AS_protected, ClangASTContext::UnifyAccessSpecifiers(AS_public, AS_protected));
+
+ // None is stricter than everything (by convention)
+ EXPECT_EQ(AS_none, ClangASTContext::UnifyAccessSpecifiers(AS_none, AS_public));
+ EXPECT_EQ(AS_none, ClangASTContext::UnifyAccessSpecifiers(AS_none, AS_protected));
+ EXPECT_EQ(AS_none, ClangASTContext::UnifyAccessSpecifiers(AS_none, AS_private));
+ EXPECT_EQ(AS_none, ClangASTContext::UnifyAccessSpecifiers(AS_public, AS_none));
+ EXPECT_EQ(AS_none, ClangASTContext::UnifyAccessSpecifiers(AS_protected, AS_none));
+ EXPECT_EQ(AS_none, ClangASTContext::UnifyAccessSpecifiers(AS_private, AS_none));
+}
+
+TEST_F(TestClangASTContext, TestRecordHasFields)
+{
+ CompilerType int_type = ClangASTContext::GetBasicType(m_ast->getASTContext(), eBasicTypeInt);
+
+ // Test that a record with no fields returns false
+ CompilerType empty_base = m_ast->CreateRecordType(nullptr, lldb::eAccessPublic, "EmptyBase", clang::TTK_Struct,
+ lldb::eLanguageTypeC_plus_plus, nullptr);
+ ClangASTContext::StartTagDeclarationDefinition(empty_base);
+ ClangASTContext::CompleteTagDeclarationDefinition(empty_base);
+
+ RecordDecl *empty_base_decl = ClangASTContext::GetAsRecordDecl(empty_base);
+ EXPECT_NE(nullptr, empty_base_decl);
+ EXPECT_FALSE(ClangASTContext::RecordHasFields(empty_base_decl));
+
+ // Test that a record with direct fields returns true
+ CompilerType non_empty_base = m_ast->CreateRecordType(nullptr, lldb::eAccessPublic, "NonEmptyBase",
+ clang::TTK_Struct, lldb::eLanguageTypeC_plus_plus, nullptr);
+ ClangASTContext::StartTagDeclarationDefinition(non_empty_base);
+ FieldDecl *non_empty_base_field_decl =
+ m_ast->AddFieldToRecordType(non_empty_base, "MyField", int_type, eAccessPublic, 0);
+ ClangASTContext::CompleteTagDeclarationDefinition(non_empty_base);
+ RecordDecl *non_empty_base_decl = ClangASTContext::GetAsRecordDecl(non_empty_base);
+ EXPECT_NE(nullptr, non_empty_base_decl);
+ EXPECT_NE(nullptr, non_empty_base_field_decl);
+ EXPECT_TRUE(ClangASTContext::RecordHasFields(non_empty_base_decl));
+
+ // Test that a record with no direct fields, but fields in a base returns true
+ CompilerType empty_derived = m_ast->CreateRecordType(nullptr, lldb::eAccessPublic, "EmptyDerived",
+ clang::TTK_Struct, lldb::eLanguageTypeC_plus_plus, nullptr);
+ ClangASTContext::StartTagDeclarationDefinition(empty_derived);
+ CXXBaseSpecifier *non_empty_base_spec =
+ m_ast->CreateBaseClassSpecifier(non_empty_base.GetOpaqueQualType(), lldb::eAccessPublic, false, false);
+ bool result = m_ast->SetBaseClassesForClassType(empty_derived.GetOpaqueQualType(), &non_empty_base_spec, 1);
+ ClangASTContext::CompleteTagDeclarationDefinition(empty_derived);
+ EXPECT_TRUE(result);
+ CXXRecordDecl *empty_derived_non_empty_base_cxx_decl = m_ast->GetAsCXXRecordDecl(empty_derived.GetOpaqueQualType());
+ RecordDecl *empty_derived_non_empty_base_decl = ClangASTContext::GetAsRecordDecl(empty_derived);
+ EXPECT_EQ(1, ClangASTContext::GetNumBaseClasses(empty_derived_non_empty_base_cxx_decl, false));
+ EXPECT_TRUE(ClangASTContext::RecordHasFields(empty_derived_non_empty_base_decl));
+
+ // Test that a record with no direct fields, but fields in a virtual base returns true
+ CompilerType empty_derived2 = m_ast->CreateRecordType(nullptr, lldb::eAccessPublic, "EmptyDerived2",
+ clang::TTK_Struct, lldb::eLanguageTypeC_plus_plus, nullptr);
+ ClangASTContext::StartTagDeclarationDefinition(empty_derived2);
+ CXXBaseSpecifier *non_empty_vbase_spec =
+ m_ast->CreateBaseClassSpecifier(non_empty_base.GetOpaqueQualType(), lldb::eAccessPublic, true, false);
+ result = m_ast->SetBaseClassesForClassType(empty_derived2.GetOpaqueQualType(), &non_empty_vbase_spec, 1);
+ ClangASTContext::CompleteTagDeclarationDefinition(empty_derived2);
+ EXPECT_TRUE(result);
+ CXXRecordDecl *empty_derived_non_empty_vbase_cxx_decl =
+ m_ast->GetAsCXXRecordDecl(empty_derived2.GetOpaqueQualType());
+ RecordDecl *empty_derived_non_empty_vbase_decl = ClangASTContext::GetAsRecordDecl(empty_derived2);
+ EXPECT_EQ(1, ClangASTContext::GetNumBaseClasses(empty_derived_non_empty_vbase_cxx_decl, false));
+ EXPECT_TRUE(ClangASTContext::RecordHasFields(empty_derived_non_empty_vbase_decl));
+}
More information about the lldb-commits
mailing list