r264529 - Improve the representation of CXXUuidofExpr
David Majnemer via cfe-commits
cfe-commits at lists.llvm.org
Sat Mar 26 21:46:07 PDT 2016
Author: majnemer
Date: Sat Mar 26 23:46:07 2016
New Revision: 264529
URL: http://llvm.org/viewvc/llvm-project?rev=264529&view=rev
Log:
Improve the representation of CXXUuidofExpr
Keep a pointer to the UuidAttr that the CXXUuidofExpr corresponds to.
This makes translating from __uuidof to the underlying constant a lot
more straightforward.
Modified:
cfe/trunk/include/clang/AST/ExprCXX.h
cfe/trunk/lib/AST/ExprCXX.cpp
cfe/trunk/lib/AST/MicrosoftMangle.cpp
cfe/trunk/lib/CodeGen/CodeGenModule.cpp
cfe/trunk/lib/Sema/SemaExprCXX.cpp
Modified: cfe/trunk/include/clang/AST/ExprCXX.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/ExprCXX.h?rev=264529&r1=264528&r2=264529&view=diff
==============================================================================
--- cfe/trunk/include/clang/AST/ExprCXX.h (original)
+++ cfe/trunk/include/clang/AST/ExprCXX.h Sat Mar 26 23:46:07 2016
@@ -778,22 +778,23 @@ public:
class CXXUuidofExpr : public Expr {
private:
llvm::PointerUnion<Stmt *, TypeSourceInfo *> Operand;
+ const UuidAttr *UA;
SourceRange Range;
public:
- CXXUuidofExpr(QualType Ty, TypeSourceInfo *Operand, SourceRange R)
- : Expr(CXXUuidofExprClass, Ty, VK_LValue, OK_Ordinary,
- false, Operand->getType()->isDependentType(),
- Operand->getType()->isInstantiationDependentType(),
- Operand->getType()->containsUnexpandedParameterPack()),
- Operand(Operand), Range(R) { }
-
- CXXUuidofExpr(QualType Ty, Expr *Operand, SourceRange R)
- : Expr(CXXUuidofExprClass, Ty, VK_LValue, OK_Ordinary,
- false, Operand->isTypeDependent(),
- Operand->isInstantiationDependent(),
- Operand->containsUnexpandedParameterPack()),
- Operand(Operand), Range(R) { }
+ CXXUuidofExpr(QualType Ty, TypeSourceInfo *Operand, const UuidAttr *UA,
+ SourceRange R)
+ : Expr(CXXUuidofExprClass, Ty, VK_LValue, OK_Ordinary, false,
+ Operand->getType()->isDependentType(),
+ Operand->getType()->isInstantiationDependentType(),
+ Operand->getType()->containsUnexpandedParameterPack()),
+ Operand(Operand), UA(UA), Range(R) {}
+
+ CXXUuidofExpr(QualType Ty, Expr *Operand, const UuidAttr *UA, SourceRange R)
+ : Expr(CXXUuidofExprClass, Ty, VK_LValue, OK_Ordinary, false,
+ Operand->isTypeDependent(), Operand->isInstantiationDependent(),
+ Operand->containsUnexpandedParameterPack()),
+ Operand(Operand), UA(UA), Range(R) {}
CXXUuidofExpr(EmptyShell Empty, bool isExpr)
: Expr(CXXUuidofExprClass, Empty) {
@@ -830,7 +831,7 @@ public:
Operand = E;
}
- StringRef getUuidAsStringRef(ASTContext &Context) const;
+ StringRef getUuidAsStringRef() const;
SourceLocation getLocStart() const LLVM_READONLY { return Range.getBegin(); }
SourceLocation getLocEnd() const LLVM_READONLY { return Range.getEnd(); }
@@ -841,11 +842,6 @@ public:
return T->getStmtClass() == CXXUuidofExprClass;
}
- /// Grabs __declspec(uuid()) off a type, or returns 0 if we cannot resolve to
- /// a single GUID.
- static const UuidAttr *GetUuidAttrOfType(QualType QT,
- bool *HasMultipleGUIDsPtr = nullptr);
-
// Iterators
child_range children() {
if (isTypeOperand())
Modified: cfe/trunk/lib/AST/ExprCXX.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/ExprCXX.cpp?rev=264529&r1=264528&r2=264529&view=diff
==============================================================================
--- cfe/trunk/lib/AST/ExprCXX.cpp (original)
+++ cfe/trunk/lib/AST/ExprCXX.cpp Sat Mar 26 23:46:07 2016
@@ -54,77 +54,8 @@ QualType CXXUuidofExpr::getTypeOperand(A
Operand.get<TypeSourceInfo *>()->getType().getNonReferenceType(), Quals);
}
-// static
-const UuidAttr *CXXUuidofExpr::GetUuidAttrOfType(QualType QT,
- bool *RDHasMultipleGUIDsPtr) {
- // Optionally remove one level of pointer, reference or array indirection.
- const Type *Ty = QT.getTypePtr();
- if (QT->isPointerType() || QT->isReferenceType())
- Ty = QT->getPointeeType().getTypePtr();
- else if (QT->isArrayType())
- Ty = Ty->getBaseElementTypeUnsafe();
-
- const CXXRecordDecl *RD = Ty->getAsCXXRecordDecl();
- if (!RD)
- return nullptr;
-
- if (const UuidAttr *Uuid = RD->getMostRecentDecl()->getAttr<UuidAttr>())
- return Uuid;
-
- // __uuidof can grab UUIDs from template arguments.
- if (const ClassTemplateSpecializationDecl *CTSD =
- dyn_cast<ClassTemplateSpecializationDecl>(RD)) {
- const TemplateArgumentList &TAL = CTSD->getTemplateArgs();
- const UuidAttr *UuidForRD = nullptr;
-
- for (const TemplateArgument &TA : TAL.asArray()) {
- bool SeenMultipleGUIDs = false;
-
- const UuidAttr *UuidForTA = nullptr;
- if (TA.getKind() == TemplateArgument::Type)
- UuidForTA = GetUuidAttrOfType(TA.getAsType(), &SeenMultipleGUIDs);
- else if (TA.getKind() == TemplateArgument::Declaration)
- UuidForTA =
- GetUuidAttrOfType(TA.getAsDecl()->getType(), &SeenMultipleGUIDs);
-
- // If the template argument has a UUID, there are three cases:
- // - This is the first UUID seen for this RecordDecl.
- // - This is a different UUID than previously seen for this RecordDecl.
- // - This is the same UUID than previously seen for this RecordDecl.
- if (UuidForTA) {
- if (!UuidForRD)
- UuidForRD = UuidForTA;
- else if (UuidForRD != UuidForTA)
- SeenMultipleGUIDs = true;
- }
-
- // Seeing multiple UUIDs means that we couldn't find a UUID
- if (SeenMultipleGUIDs) {
- if (RDHasMultipleGUIDsPtr)
- *RDHasMultipleGUIDsPtr = true;
- return nullptr;
- }
- }
-
- return UuidForRD;
- }
-
- return nullptr;
-}
-
-StringRef CXXUuidofExpr::getUuidAsStringRef(ASTContext &Context) const {
- StringRef Uuid;
- if (isTypeOperand())
- Uuid = CXXUuidofExpr::GetUuidAttrOfType(getTypeOperand(Context))->getGuid();
- else {
- // Special case: __uuidof(0) means an all-zero GUID.
- Expr *Op = getExprOperand();
- if (!Op->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNull))
- Uuid = CXXUuidofExpr::GetUuidAttrOfType(Op->getType())->getGuid();
- else
- Uuid = "00000000-0000-0000-0000-000000000000";
- }
- return Uuid;
+StringRef CXXUuidofExpr::getUuidAsStringRef() const {
+ return UA ? UA->getGuid() : "00000000-0000-0000-0000-000000000000";
}
// CXXScalarValueInitExpr
Modified: cfe/trunk/lib/AST/MicrosoftMangle.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/MicrosoftMangle.cpp?rev=264529&r1=264528&r2=264529&view=diff
==============================================================================
--- cfe/trunk/lib/AST/MicrosoftMangle.cpp (original)
+++ cfe/trunk/lib/AST/MicrosoftMangle.cpp Sat Mar 26 23:46:07 2016
@@ -1186,7 +1186,7 @@ void MicrosoftCXXNameMangler::mangleExpr
// This CXXUuidofExpr is mangled as-if it were actually a VarDecl from
// const __s_GUID _GUID_{lower case UUID with underscores}
- StringRef Uuid = UE->getUuidAsStringRef(Context.getASTContext());
+ StringRef Uuid = UE->getUuidAsStringRef();
std::string Name = "_GUID_" + Uuid.lower();
std::replace(Name.begin(), Name.end(), '-', '_');
Modified: cfe/trunk/lib/CodeGen/CodeGenModule.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CodeGenModule.cpp?rev=264529&r1=264528&r2=264529&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/CodeGenModule.cpp (original)
+++ cfe/trunk/lib/CodeGen/CodeGenModule.cpp Sat Mar 26 23:46:07 2016
@@ -1454,7 +1454,7 @@ ConstantAddress CodeGenModule::GetAddrOf
const CXXUuidofExpr* E) {
// Sema has verified that IIDSource has a __declspec(uuid()), and that its
// well-formed.
- StringRef Uuid = E->getUuidAsStringRef(Context);
+ StringRef Uuid = E->getUuidAsStringRef();
std::string Name = "_GUID_" + Uuid.lower();
std::replace(Name.begin(), Name.end(), '-', '_');
Modified: cfe/trunk/lib/Sema/SemaExprCXX.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaExprCXX.cpp?rev=264529&r1=264528&r2=264529&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaExprCXX.cpp (original)
+++ cfe/trunk/lib/Sema/SemaExprCXX.cpp Sat Mar 26 23:46:07 2016
@@ -508,23 +508,60 @@ Sema::ActOnCXXTypeid(SourceLocation OpLo
return BuildCXXTypeId(TypeInfoType, OpLoc, (Expr*)TyOrExpr, RParenLoc);
}
+/// Grabs __declspec(uuid()) off a type, or returns 0 if we cannot resolve to
+/// a single GUID.
+static void
+getUuidAttrOfType(Sema &SemaRef, QualType QT,
+ llvm::SmallSetVector<const UuidAttr *, 1> &UuidAttrs) {
+ // Optionally remove one level of pointer, reference or array indirection.
+ const Type *Ty = QT.getTypePtr();
+ if (QT->isPointerType() || QT->isReferenceType())
+ Ty = QT->getPointeeType().getTypePtr();
+ else if (QT->isArrayType())
+ Ty = Ty->getBaseElementTypeUnsafe();
+
+ const auto *RD = Ty->getAsCXXRecordDecl();
+ if (!RD)
+ return;
+
+ if (const auto *Uuid = RD->getMostRecentDecl()->getAttr<UuidAttr>()) {
+ UuidAttrs.insert(Uuid);
+ return;
+ }
+
+ // __uuidof can grab UUIDs from template arguments.
+ if (const auto *CTSD = dyn_cast<ClassTemplateSpecializationDecl>(RD)) {
+ const TemplateArgumentList &TAL = CTSD->getTemplateArgs();
+ for (const TemplateArgument &TA : TAL.asArray()) {
+ const UuidAttr *UuidForTA = nullptr;
+ if (TA.getKind() == TemplateArgument::Type)
+ getUuidAttrOfType(SemaRef, TA.getAsType(), UuidAttrs);
+ else if (TA.getKind() == TemplateArgument::Declaration)
+ getUuidAttrOfType(SemaRef, TA.getAsDecl()->getType(), UuidAttrs);
+
+ if (UuidForTA)
+ UuidAttrs.insert(UuidForTA);
+ }
+ }
+}
+
/// \brief Build a Microsoft __uuidof expression with a type operand.
ExprResult Sema::BuildCXXUuidof(QualType TypeInfoType,
SourceLocation TypeidLoc,
TypeSourceInfo *Operand,
SourceLocation RParenLoc) {
+ const UuidAttr *UA = nullptr;
if (!Operand->getType()->isDependentType()) {
- bool HasMultipleGUIDs = false;
- if (!CXXUuidofExpr::GetUuidAttrOfType(Operand->getType(),
- &HasMultipleGUIDs)) {
- if (HasMultipleGUIDs)
- return ExprError(Diag(TypeidLoc, diag::err_uuidof_with_multiple_guids));
- else
- return ExprError(Diag(TypeidLoc, diag::err_uuidof_without_guid));
- }
+ llvm::SmallSetVector<const UuidAttr *, 1> UuidAttrs;
+ getUuidAttrOfType(*this, Operand->getType(), UuidAttrs);
+ if (UuidAttrs.empty())
+ return ExprError(Diag(TypeidLoc, diag::err_uuidof_without_guid));
+ if (UuidAttrs.size() > 1)
+ return ExprError(Diag(TypeidLoc, diag::err_uuidof_with_multiple_guids));
+ UA = UuidAttrs.back();
}
- return new (Context) CXXUuidofExpr(TypeInfoType.withConst(), Operand,
+ return new (Context) CXXUuidofExpr(TypeInfoType.withConst(), Operand, UA,
SourceRange(TypeidLoc, RParenLoc));
}
@@ -533,18 +570,20 @@ ExprResult Sema::BuildCXXUuidof(QualType
SourceLocation TypeidLoc,
Expr *E,
SourceLocation RParenLoc) {
+ const UuidAttr *UA = nullptr;
if (!E->getType()->isDependentType()) {
- bool HasMultipleGUIDs = false;
- if (!CXXUuidofExpr::GetUuidAttrOfType(E->getType(), &HasMultipleGUIDs) &&
- !E->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNull)) {
- if (HasMultipleGUIDs)
- return ExprError(Diag(TypeidLoc, diag::err_uuidof_with_multiple_guids));
- else
+ if (!E->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNull)) {
+ llvm::SmallSetVector<const UuidAttr *, 1> UuidAttrs;
+ getUuidAttrOfType(*this, E->getType(), UuidAttrs);
+ if (UuidAttrs.empty())
return ExprError(Diag(TypeidLoc, diag::err_uuidof_without_guid));
+ if (UuidAttrs.size() > 1)
+ return ExprError(Diag(TypeidLoc, diag::err_uuidof_with_multiple_guids));
+ UA = UuidAttrs.back();
}
}
- return new (Context) CXXUuidofExpr(TypeInfoType.withConst(), E,
+ return new (Context) CXXUuidofExpr(TypeInfoType.withConst(), E, UA,
SourceRange(TypeidLoc, RParenLoc));
}
More information about the cfe-commits
mailing list