summaryrefslogtreecommitdiffstats
path: root/clang/lib/Sema/SemaExprCXX.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'clang/lib/Sema/SemaExprCXX.cpp')
-rw-r--r--clang/lib/Sema/SemaExprCXX.cpp51
1 files changed, 32 insertions, 19 deletions
diff --git a/clang/lib/Sema/SemaExprCXX.cpp b/clang/lib/Sema/SemaExprCXX.cpp
index 4b7db59444b..da34791395b 100644
--- a/clang/lib/Sema/SemaExprCXX.cpp
+++ b/clang/lib/Sema/SemaExprCXX.cpp
@@ -3550,27 +3550,43 @@ static bool CheckUnaryTypeTraitTypeCompleteness(Sema &S, TypeTrait UTT,
case UTT_IsVolatile:
case UTT_IsSigned:
case UTT_IsUnsigned:
+
+ // This type trait always returns false, checking the type is moot.
+ case UTT_IsInterfaceClass:
+ return true;
+
+ // C++14 [meta.unary.prop]:
+ // If T is a non-union class type, T shall be a complete type.
+ case UTT_IsEmpty:
+ case UTT_IsPolymorphic:
+ case UTT_IsAbstract:
+ if (const auto *RD = ArgTy->getAsCXXRecordDecl())
+ if (!RD->isUnion())
+ return !S.RequireCompleteType(
+ Loc, ArgTy, diag::err_incomplete_type_used_in_type_trait_expr);
+ return true;
+
+ // C++14 [meta.unary.prop]:
+ // If T is a class type, T shall be a complete type.
+ case UTT_IsFinal:
+ case UTT_IsSealed:
+ if (ArgTy->getAsCXXRecordDecl())
+ return !S.RequireCompleteType(
+ Loc, ArgTy, diag::err_incomplete_type_used_in_type_trait_expr);
return true;
- // C++0x [meta.unary.prop] Table 49 requires the following traits to be
- // applied to a complete type.
+ // C++0x [meta.unary.prop] Table 49 requires the following traits to be
+ // applied to a complete type.
case UTT_IsTrivial:
case UTT_IsTriviallyCopyable:
case UTT_IsStandardLayout:
case UTT_IsPOD:
case UTT_IsLiteral:
- case UTT_IsEmpty:
- case UTT_IsPolymorphic:
- case UTT_IsAbstract:
- case UTT_IsInterfaceClass:
+
case UTT_IsDestructible:
case UTT_IsNothrowDestructible:
// Fall-through
- // These traits require a complete type.
- case UTT_IsFinal:
- case UTT_IsSealed:
-
// These trait expressions are designed to help implement predicates in
// [meta.unary.prop] despite not being named the same. They are specified
// by both GCC and the Embarcadero C++ compiler, and require the complete
@@ -3729,24 +3745,21 @@ static bool EvaluateUnaryTypeTrait(Sema &Self, TypeTrait UTT,
return false;
case UTT_IsPolymorphic:
if (const CXXRecordDecl *RD = T->getAsCXXRecordDecl())
- return RD->isPolymorphic();
+ return !RD->isUnion() && RD->isPolymorphic();
return false;
case UTT_IsAbstract:
if (const CXXRecordDecl *RD = T->getAsCXXRecordDecl())
- return RD->isAbstract();
+ return !RD->isUnion() && RD->isAbstract();
return false;
+ // __is_interface_class only returns true when CL is invoked in /CLR mode and
+ // even then only when it is used with the 'interface struct ...' syntax
+ // Clang doesn't support /CLR which makes this type trait moot.
case UTT_IsInterfaceClass:
- if (const CXXRecordDecl *RD = T->getAsCXXRecordDecl())
- return RD->isInterface();
return false;
case UTT_IsFinal:
- if (const CXXRecordDecl *RD = T->getAsCXXRecordDecl())
- return RD->hasAttr<FinalAttr>();
- return false;
case UTT_IsSealed:
if (const CXXRecordDecl *RD = T->getAsCXXRecordDecl())
- if (FinalAttr *FA = RD->getAttr<FinalAttr>())
- return FA->isSpelledAsSealed();
+ return RD->hasAttr<FinalAttr>();
return false;
case UTT_IsSigned:
return T->isSignedIntegerType();
OpenPOWER on IntegriCloud