summaryrefslogtreecommitdiffstats
path: root/lib/Sema/SemaDeclCXX.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'lib/Sema/SemaDeclCXX.cpp')
-rw-r--r--lib/Sema/SemaDeclCXX.cpp246
1 files changed, 129 insertions, 117 deletions
diff --git a/lib/Sema/SemaDeclCXX.cpp b/lib/Sema/SemaDeclCXX.cpp
index 43b289d8d0..7e4aab0fae 100644
--- a/lib/Sema/SemaDeclCXX.cpp
+++ b/lib/Sema/SemaDeclCXX.cpp
@@ -1,9 +1,8 @@
//===------ SemaDeclCXX.cpp - Semantic Analysis for C++ Declarations ------===//
//
-// The LLVM Compiler Infrastructure
-//
-// This file is distributed under the University of Illinois Open Source
-// License. See LICENSE.TXT for details.
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//
//
@@ -1129,7 +1128,6 @@ static bool checkTupleLikeDecomposition(Sema &S,
}
}
}
- S.FilterAcceptableTemplateNames(MemberGet);
}
unsigned I = 0;
@@ -1301,6 +1299,10 @@ static DeclAccessPair findDecomposableBaseClass(Sema &S, SourceLocation Loc,
static bool checkMemberDecomposition(Sema &S, ArrayRef<BindingDecl*> Bindings,
ValueDecl *Src, QualType DecompType,
const CXXRecordDecl *OrigRD) {
+ if (S.RequireCompleteType(Src->getLocation(), DecompType,
+ diag::err_incomplete_type))
+ return true;
+
CXXCastPath BasePath;
DeclAccessPair BasePair =
findDecomposableBaseClass(S, Src->getLocation(), OrigRD, BasePath);
@@ -3172,7 +3174,11 @@ Sema::ActOnCXXMemberDeclarator(Scope *S, AccessSpecifier AS, Declarator &D,
// declared] with the same access [as the template].
if (auto *DG = dyn_cast<CXXDeductionGuideDecl>(NonTemplateMember)) {
auto *TD = DG->getDeducedTemplate();
- if (AS != TD->getAccess()) {
+ // Access specifiers are only meaningful if both the template and the
+ // deduction guide are from the same scope.
+ if (AS != TD->getAccess() &&
+ TD->getDeclContext()->getRedeclContext()->Equals(
+ DG->getDeclContext()->getRedeclContext())) {
Diag(DG->getBeginLoc(), diag::err_deduction_guide_wrong_access);
Diag(TD->getBeginLoc(), diag::note_deduction_guide_template_access)
<< TD->getAccess();
@@ -3775,7 +3781,7 @@ namespace {
// Callback to only accept typo corrections that can be a valid C++ member
// intializer: either a non-static field member or a base class.
-class MemInitializerValidatorCCC : public CorrectionCandidateCallback {
+class MemInitializerValidatorCCC final : public CorrectionCandidateCallback {
public:
explicit MemInitializerValidatorCCC(CXXRecordDecl *ClassDecl)
: ClassDecl(ClassDecl) {}
@@ -3789,6 +3795,10 @@ public:
return false;
}
+ std::unique_ptr<CorrectionCandidateCallback> clone() override {
+ return llvm::make_unique<MemInitializerValidatorCCC>(*this);
+ }
+
private:
CXXRecordDecl *ClassDecl;
};
@@ -3918,11 +3928,10 @@ Sema::BuildMemInitializer(Decl *ConstructorD,
// If no results were found, try to correct typos.
TypoCorrection Corr;
+ MemInitializerValidatorCCC CCC(ClassDecl);
if (R.empty() && BaseType.isNull() &&
- (Corr = CorrectTypo(
- R.getLookupNameInfo(), R.getLookupKind(), S, &SS,
- llvm::make_unique<MemInitializerValidatorCCC>(ClassDecl),
- CTK_ErrorRecovery, ClassDecl))) {
+ (Corr = CorrectTypo(R.getLookupNameInfo(), R.getLookupKind(), S, &SS,
+ CCC, CTK_ErrorRecovery, ClassDecl))) {
if (FieldDecl *Member = Corr.getCorrectionDeclAs<FieldDecl>()) {
// We have found a non-static data member with a similar
// name to what was typed; complain and initialize that
@@ -5688,9 +5697,11 @@ void Sema::checkClassLevelDLLAttribute(CXXRecordDecl *Class) {
TemplateSpecializationKind TSK = Class->getTemplateSpecializationKind();
- // Ignore explicit dllexport on explicit class template instantiation declarations.
+ // Ignore explicit dllexport on explicit class template instantiation
+ // declarations, except in MinGW mode.
if (ClassExported && !ClassAttr->isInherited() &&
- TSK == TSK_ExplicitInstantiationDeclaration) {
+ TSK == TSK_ExplicitInstantiationDeclaration &&
+ !Context.getTargetInfo().getTriple().isWindowsGNUEnvironment()) {
Class->dropAttr<DLLExportAttr>();
return;
}
@@ -5715,9 +5726,12 @@ void Sema::checkClassLevelDLLAttribute(CXXRecordDecl *Class) {
continue;
if (MD->isInlined()) {
- // MinGW does not import or export inline methods.
+ // MinGW does not import or export inline methods. But do it for
+ // template instantiations.
if (!Context.getTargetInfo().getCXXABI().isMicrosoft() &&
- !Context.getTargetInfo().getTriple().isWindowsItaniumEnvironment())
+ !Context.getTargetInfo().getTriple().isWindowsItaniumEnvironment() &&
+ TSK != TSK_ExplicitInstantiationDeclaration &&
+ TSK != TSK_ExplicitInstantiationDefinition)
continue;
// MSVC versions before 2015 don't export the move assignment operators
@@ -5886,9 +5900,6 @@ static bool canPassInRegisters(Sema &S, CXXRecordDecl *D,
if (D->isDependentType() || D->isInvalidDecl())
return false;
- if (D->hasAttr<TrivialABIAttr>())
- return true;
-
// Clang <= 4 used the pre-C++11 rule, which ignores move operations.
// The PS4 platform ABI follows the behavior of Clang 3.2.
if (CCK == TargetInfo::CCK_ClangABI4OrPS4)
@@ -5946,8 +5957,11 @@ static bool canPassInRegisters(Sema &S, CXXRecordDecl *D,
// Note: This permits small classes with nontrivial destructors to be
// passed in registers, which is non-conforming.
+ bool isAArch64 = S.Context.getTargetInfo().getTriple().isAArch64();
+ uint64_t TypeSize = isAArch64 ? 128 : 64;
+
if (CopyCtorIsTrivial &&
- S.getASTContext().getTypeSize(D->getTypeForDecl()) <= 64)
+ S.getASTContext().getTypeSize(D->getTypeForDecl()) <= TypeSize)
return true;
return false;
}
@@ -6553,7 +6567,7 @@ void Sema::CheckExplicitlyDefaultedSpecialMember(CXXMethodDecl *MD) {
ReturnType = Type->getReturnType();
QualType DeclType = Context.getTypeDeclType(RD);
- DeclType = Context.getAddrSpaceQualType(DeclType, MD->getTypeQualifiers().getAddressSpace());
+ DeclType = Context.getAddrSpaceQualType(DeclType, MD->getMethodQualifiers().getAddressSpace());
QualType ExpectedReturnType = Context.getLValueReferenceType(DeclType);
if (!Context.hasSameType(ReturnType, ExpectedReturnType)) {
@@ -6563,7 +6577,7 @@ void Sema::CheckExplicitlyDefaultedSpecialMember(CXXMethodDecl *MD) {
}
// A defaulted special member cannot have cv-qualifiers.
- if (Type->getTypeQuals().hasConst() || Type->getTypeQuals().hasVolatile()) {
+ if (Type->getMethodQuals().hasConst() || Type->getMethodQuals().hasVolatile()) {
if (DeleteOnTypeMismatch)
ShouldDeleteForTypeMismatch = true;
else {
@@ -6623,6 +6637,8 @@ void Sema::CheckExplicitlyDefaultedSpecialMember(CXXMethodDecl *MD) {
// makes such functions always instantiate to constexpr functions. For
// functions which cannot be constexpr (for non-constructors in C++11 and for
// destructors in C++1y), this is checked elsewhere.
+ //
+ // FIXME: This should not apply if the member is deleted.
bool Constexpr = defaultedSpecialMemberIsConstexpr(*this, RD, CSM,
HasConstParam);
if ((getLangOpts().CPlusPlus14 ? !isa<CXXDestructorDecl>(MD)
@@ -6634,38 +6650,26 @@ void Sema::CheckExplicitlyDefaultedSpecialMember(CXXMethodDecl *MD) {
HadError = true;
}
- // and may have an explicit exception-specification only if it is compatible
- // with the exception-specification on the implicit declaration.
- if (Type->hasExceptionSpec()) {
- // Delay the check if this is the first declaration of the special member,
- // since we may not have parsed some necessary in-class initializers yet.
- if (First) {
- // If the exception specification needs to be instantiated, do so now,
- // before we clobber it with an EST_Unevaluated specification below.
- if (Type->getExceptionSpecType() == EST_Uninstantiated) {
- InstantiateExceptionSpec(MD->getBeginLoc(), MD);
- Type = MD->getType()->getAs<FunctionProtoType>();
- }
- DelayedDefaultedMemberExceptionSpecs.push_back(std::make_pair(MD, Type));
- } else
- CheckExplicitlyDefaultedMemberExceptionSpec(MD, Type);
- }
-
- // If a function is explicitly defaulted on its first declaration,
if (First) {
- // -- it is implicitly considered to be constexpr if the implicit
- // definition would be,
+ // C++2a [dcl.fct.def.default]p3:
+ // If a function is explicitly defaulted on its first declaration, it is
+ // implicitly considered to be constexpr if the implicit declaration
+ // would be.
MD->setConstexpr(Constexpr);
- // -- it is implicitly considered to have the same exception-specification
- // as if it had been implicitly declared,
- FunctionProtoType::ExtProtoInfo EPI = Type->getExtProtoInfo();
- EPI.ExceptionSpec.Type = EST_Unevaluated;
- EPI.ExceptionSpec.SourceDecl = MD;
- MD->setType(Context.getFunctionType(ReturnType,
- llvm::makeArrayRef(&ArgType,
- ExpectedParams),
- EPI));
+ if (!Type->hasExceptionSpec()) {
+ // C++2a [except.spec]p3:
+ // If a declaration of a function does not have a noexcept-specifier
+ // [and] is defaulted on its first declaration, [...] the exception
+ // specification is as specified below
+ FunctionProtoType::ExtProtoInfo EPI = Type->getExtProtoInfo();
+ EPI.ExceptionSpec.Type = EST_Unevaluated;
+ EPI.ExceptionSpec.SourceDecl = MD;
+ MD->setType(Context.getFunctionType(ReturnType,
+ llvm::makeArrayRef(&ArgType,
+ ExpectedParams),
+ EPI));
+ }
}
if (ShouldDeleteForTypeMismatch || ShouldDeleteSpecialMember(MD, CSM)) {
@@ -6698,43 +6702,12 @@ void Sema::CheckExplicitlyDefaultedSpecialMember(CXXMethodDecl *MD) {
MD->setInvalidDecl();
}
-/// Check whether the exception specification provided for an
-/// explicitly-defaulted special member matches the exception specification
-/// that would have been generated for an implicit special member, per
-/// C++11 [dcl.fct.def.default]p2.
-void Sema::CheckExplicitlyDefaultedMemberExceptionSpec(
- CXXMethodDecl *MD, const FunctionProtoType *SpecifiedType) {
- // If the exception specification was explicitly specified but hadn't been
- // parsed when the method was defaulted, grab it now.
- if (SpecifiedType->getExceptionSpecType() == EST_Unparsed)
- SpecifiedType =
- MD->getTypeSourceInfo()->getType()->castAs<FunctionProtoType>();
-
- // Compute the implicit exception specification.
- CallingConv CC = Context.getDefaultCallingConvention(/*IsVariadic=*/false,
- /*IsCXXMethod=*/true);
- FunctionProtoType::ExtProtoInfo EPI(CC);
- auto IES = computeImplicitExceptionSpec(*this, MD->getLocation(), MD);
- EPI.ExceptionSpec = IES.getExceptionSpec();
- const FunctionProtoType *ImplicitType = cast<FunctionProtoType>(
- Context.getFunctionType(Context.VoidTy, None, EPI));
-
- // Ensure that it matches.
- CheckEquivalentExceptionSpec(
- PDiag(diag::err_incorrect_defaulted_exception_spec)
- << getSpecialMember(MD), PDiag(),
- ImplicitType, SourceLocation(),
- SpecifiedType, MD->getLocation());
-}
-
void Sema::CheckDelayedMemberExceptionSpecs() {
decltype(DelayedOverridingExceptionSpecChecks) Overriding;
decltype(DelayedEquivalentExceptionSpecChecks) Equivalent;
- decltype(DelayedDefaultedMemberExceptionSpecs) Defaulted;
std::swap(Overriding, DelayedOverridingExceptionSpecChecks);
std::swap(Equivalent, DelayedEquivalentExceptionSpecChecks);
- std::swap(Defaulted, DelayedDefaultedMemberExceptionSpecs);
// Perform any deferred checking of exception specifications for virtual
// destructors.
@@ -6745,11 +6718,6 @@ void Sema::CheckDelayedMemberExceptionSpecs() {
// special members.
for (auto &Check : Equivalent)
CheckEquivalentExceptionSpec(Check.second, Check.first);
-
- // Check that any explicitly-defaulted methods have exception specifications
- // compatible with their implicit exception specifications.
- for (auto &Spec : Defaulted)
- CheckExplicitlyDefaultedMemberExceptionSpec(Spec.first, Spec.second);
}
namespace {
@@ -6891,6 +6859,8 @@ struct SpecialMemberDeletionInfo
return ICI ? Sema::CXXInvalid : CSM;
}
+ bool shouldDeleteForVariantObjCPtrMember(FieldDecl *FD, QualType FieldType);
+
bool visitBase(CXXBaseSpecifier *Base) { return shouldDeleteForBase(Base); }
bool visitField(FieldDecl *Field) { return shouldDeleteForField(Field); }
@@ -6962,13 +6932,14 @@ bool SpecialMemberDeletionInfo::shouldDeleteForSubobjectCall(
S.Diag(Field->getLocation(),
diag::note_deleted_special_member_class_subobject)
<< getEffectiveCSM() << MD->getParent() << /*IsField*/true
- << Field << DiagKind << IsDtorCallInCtor;
+ << Field << DiagKind << IsDtorCallInCtor << /*IsObjCPtr*/false;
} else {
CXXBaseSpecifier *Base = Subobj.get<CXXBaseSpecifier*>();
S.Diag(Base->getBeginLoc(),
diag::note_deleted_special_member_class_subobject)
<< getEffectiveCSM() << MD->getParent() << /*IsField*/ false
- << Base->getType() << DiagKind << IsDtorCallInCtor;
+ << Base->getType() << DiagKind << IsDtorCallInCtor
+ << /*IsObjCPtr*/false;
}
if (DiagKind == 1)
@@ -7020,6 +6991,30 @@ bool SpecialMemberDeletionInfo::shouldDeleteForClassSubobject(
return false;
}
+bool SpecialMemberDeletionInfo::shouldDeleteForVariantObjCPtrMember(
+ FieldDecl *FD, QualType FieldType) {
+ // The defaulted special functions are defined as deleted if this is a variant
+ // member with a non-trivial ownership type, e.g., ObjC __strong or __weak
+ // type under ARC.
+ if (!FieldType.hasNonTrivialObjCLifetime())
+ return false;
+
+ // Don't make the defaulted default constructor defined as deleted if the
+ // member has an in-class initializer.
+ if (CSM == Sema::CXXDefaultConstructor && FD->hasInClassInitializer())
+ return false;
+
+ if (Diagnose) {
+ auto *ParentClass = cast<CXXRecordDecl>(FD->getParent());
+ S.Diag(FD->getLocation(),
+ diag::note_deleted_special_member_class_subobject)
+ << getEffectiveCSM() << ParentClass << /*IsField*/true
+ << FD << 4 << /*IsDtorCallInCtor*/false << /*IsObjCPtr*/true;
+ }
+
+ return true;
+}
+
/// Check whether we should delete a special member function due to the class
/// having a particular direct or virtual base class.
bool SpecialMemberDeletionInfo::shouldDeleteForBase(CXXBaseSpecifier *Base) {
@@ -7040,7 +7035,8 @@ bool SpecialMemberDeletionInfo::shouldDeleteForBase(CXXBaseSpecifier *Base) {
S.Diag(Base->getBeginLoc(),
diag::note_deleted_special_member_class_subobject)
<< getEffectiveCSM() << MD->getParent() << /*IsField*/ false
- << Base->getType() << /*Deleted*/ 1 << /*IsDtorCallInCtor*/ false;
+ << Base->getType() << /*Deleted*/ 1 << /*IsDtorCallInCtor*/ false
+ << /*IsObjCPtr*/false;
S.NoteDeletedFunction(BaseCtor);
}
return BaseCtor->isDeleted();
@@ -7054,6 +7050,9 @@ bool SpecialMemberDeletionInfo::shouldDeleteForField(FieldDecl *FD) {
QualType FieldType = S.Context.getBaseElementType(FD->getType());
CXXRecordDecl *FieldRecord = FieldType->getAsCXXRecordDecl();
+ if (inUnion() && shouldDeleteForVariantObjCPtrMember(FD, FieldType))
+ return true;
+
if (CSM == Sema::CXXDefaultConstructor) {
// For a default constructor, all references must be initialized in-class
// and, if a union, it must have a non-const member.
@@ -7115,6 +7114,9 @@ bool SpecialMemberDeletionInfo::shouldDeleteForField(FieldDecl *FD) {
for (auto *UI : FieldRecord->fields()) {
QualType UnionFieldType = S.Context.getBaseElementType(UI->getType());
+ if (shouldDeleteForVariantObjCPtrMember(&*UI, UnionFieldType))
+ return true;
+
if (!UnionFieldType.isConstQualified())
AllVariantFieldsAreConst = false;
@@ -7934,14 +7936,14 @@ void Sema::ActOnFinishCXXMemberSpecification(
/// definition of the class is complete.
void Sema::AddImplicitlyDeclaredMembersToClass(CXXRecordDecl *ClassDecl) {
if (ClassDecl->needsImplicitDefaultConstructor()) {
- ++ASTContext::NumImplicitDefaultConstructors;
+ ++getASTContext().NumImplicitDefaultConstructors;
if (ClassDecl->hasInheritedConstructor())
DeclareImplicitDefaultConstructor(ClassDecl);
}
if (ClassDecl->needsImplicitCopyConstructor()) {
- ++ASTContext::NumImplicitCopyConstructors;
+ ++getASTContext().NumImplicitCopyConstructors;
// If the properties or semantics of the copy constructor couldn't be
// determined while the class was being declared, force a declaration
@@ -7963,7 +7965,7 @@ void Sema::AddImplicitlyDeclaredMembersToClass(CXXRecordDecl *ClassDecl) {
}
if (getLangOpts().CPlusPlus11 && ClassDecl->needsImplicitMoveConstructor()) {
- ++ASTContext::NumImplicitMoveConstructors;
+ ++getASTContext().NumImplicitMoveConstructors;
if (ClassDecl->needsOverloadResolutionForMoveConstructor() ||
ClassDecl->hasInheritedConstructor())
@@ -7971,7 +7973,7 @@ void Sema::AddImplicitlyDeclaredMembersToClass(CXXRecordDecl *ClassDecl) {
}
if (ClassDecl->needsImplicitCopyAssignment()) {
- ++ASTContext::NumImplicitCopyAssignmentOperators;
+ ++getASTContext().NumImplicitCopyAssignmentOperators;
// If we have a dynamic class, then the copy assignment operator may be
// virtual, so we have to declare it immediately. This ensures that, e.g.,
@@ -7984,7 +7986,7 @@ void Sema::AddImplicitlyDeclaredMembersToClass(CXXRecordDecl *ClassDecl) {
}
if (getLangOpts().CPlusPlus11 && ClassDecl->needsImplicitMoveAssignment()) {
- ++ASTContext::NumImplicitMoveAssignmentOperators;
+ ++getASTContext().NumImplicitMoveAssignmentOperators;
// Likewise for the move assignment operator.
if (ClassDecl->isDynamicClass() ||
@@ -7994,7 +7996,7 @@ void Sema::AddImplicitlyDeclaredMembersToClass(CXXRecordDecl *ClassDecl) {
}
if (ClassDecl->needsImplicitDestructor()) {
- ++ASTContext::NumImplicitDestructors;
+ ++getASTContext().NumImplicitDestructors;
// If we have a dynamic class, then the destructor may be virtual, so we
// have to declare the destructor immediately. This ensures that, e.g., it
@@ -8997,6 +8999,9 @@ void Sema::ActOnFinishNamespaceDef(Decl *Dcl, SourceLocation RBrace) {
PopDeclContext();
if (Namespc->hasAttr<VisibilityAttr>())
PopPragmaVisibility(true, RBrace);
+ // If this namespace contains an export-declaration, export it now.
+ if (DeferredExportedNamespaces.erase(Namespc))
+ Dcl->setModuleOwnershipKind(Decl::ModuleOwnershipKind::VisibleWhenImported);
}
CXXRecordDecl *Sema::getStdBadAlloc() const {
@@ -9316,13 +9321,17 @@ static bool IsUsingDirectiveInToplevelContext(DeclContext *CurContext) {
namespace {
// Callback to only accept typo corrections that are namespaces.
-class NamespaceValidatorCCC : public CorrectionCandidateCallback {
+class NamespaceValidatorCCC final : public CorrectionCandidateCallback {
public:
bool ValidateCandidate(const TypoCorrection &candidate) override {
if (NamedDecl *ND = candidate.getCorrectionDecl())
return isa<NamespaceDecl>(ND) || isa<NamespaceAliasDecl>(ND);
return false;
}
+
+ std::unique_ptr<CorrectionCandidateCallback> clone() override {
+ return llvm::make_unique<NamespaceValidatorCCC>(*this);
+ }
};
}
@@ -9332,9 +9341,9 @@ static bool TryNamespaceTypoCorrection(Sema &S, LookupResult &R, Scope *Sc,
SourceLocation IdentLoc,
IdentifierInfo *Ident) {
R.clear();
+ NamespaceValidatorCCC CCC{};
if (TypoCorrection Corrected =
- S.CorrectTypo(R.getLookupNameInfo(), R.getLookupKind(), Sc, &SS,
- llvm::make_unique<NamespaceValidatorCCC>(),
+ S.CorrectTypo(R.getLookupNameInfo(), R.getLookupKind(), Sc, &SS, CCC,
Sema::CTK_ErrorRecovery)) {
if (DeclContext *DC = S.computeDeclContext(SS, false)) {
std::string CorrectedStr(Corrected.getAsString(S.getLangOpts()));
@@ -9829,7 +9838,7 @@ static CXXBaseSpecifier *findDirectBaseWithType(CXXRecordDecl *Derived,
}
namespace {
-class UsingValidatorCCC : public CorrectionCandidateCallback {
+class UsingValidatorCCC final : public CorrectionCandidateCallback {
public:
UsingValidatorCCC(bool HasTypenameKeyword, bool IsInstantiation,
NestedNameSpecifier *NNS, CXXRecordDecl *RequireMemberOf)
@@ -9899,6 +9908,10 @@ public:
return !HasTypenameKeyword;
}
+ std::unique_ptr<CorrectionCandidateCallback> clone() override {
+ return llvm::make_unique<UsingValidatorCCC>(*this);
+ }
+
private:
bool HasTypenameKeyword;
bool IsInstantiation;
@@ -10055,12 +10068,11 @@ NamedDecl *Sema::BuildUsingDeclaration(
isa<TranslationUnitDecl>(LookupContext) &&
getSourceManager().isInSystemHeader(UsingLoc))
return nullptr;
- if (TypoCorrection Corrected = CorrectTypo(
- R.getLookupNameInfo(), R.getLookupKind(), S, &SS,
- llvm::make_unique<UsingValidatorCCC>(
- HasTypenameKeyword, IsInstantiation, SS.getScopeRep(),
- dyn_cast<CXXRecordDecl>(CurContext)),
- CTK_ErrorRecovery)) {
+ UsingValidatorCCC CCC(HasTypenameKeyword, IsInstantiation, SS.getScopeRep(),
+ dyn_cast<CXXRecordDecl>(CurContext));
+ if (TypoCorrection Corrected =
+ CorrectTypo(R.getLookupNameInfo(), R.getLookupKind(), S, &SS, CCC,
+ CTK_ErrorRecovery)) {
// We reject candidates where DroppedSpecifier == true, hence the
// literal '0' below.
diagnoseTypo(Corrected, PDiag(diag::err_no_member_suggest)
@@ -10976,7 +10988,7 @@ CXXConstructorDecl *Sema::DeclareImplicitDefaultConstructor(
DefaultCon->setTrivial(ClassDecl->hasTrivialDefaultConstructor());
// Note that we have declared this constructor.
- ++ASTContext::NumImplicitDefaultConstructorsDeclared;
+ ++getASTContext().NumImplicitDefaultConstructorsDeclared;
Scope *S = getScopeForContext(ClassDecl);
CheckImplicitSpecialMemberDeclaration(S, DefaultCon);
@@ -11249,7 +11261,7 @@ CXXDestructorDecl *Sema::DeclareImplicitDestructor(CXXRecordDecl *ClassDecl) {
ClassDecl->hasTrivialDestructorForCall());
// Note that we have declared this destructor.
- ++ASTContext::NumImplicitDestructorsDeclared;
+ ++getASTContext().NumImplicitDestructorsDeclared;
Scope *S = getScopeForContext(ClassDecl);
CheckImplicitSpecialMemberDeclaration(S, Destructor);
@@ -11319,7 +11331,6 @@ void Sema::ActOnFinishCXXMemberDecls() {
if (Record->isInvalidDecl()) {
DelayedOverridingExceptionSpecChecks.clear();
DelayedEquivalentExceptionSpecChecks.clear();
- DelayedDefaultedMemberExceptionSpecs.clear();
return;
}
checkForMultipleExportedDefaultConstructors(*this, Record);
@@ -11810,14 +11821,13 @@ CXXMethodDecl *Sema::DeclareImplicitCopyAssignment(CXXRecordDecl *ClassDecl) {
return nullptr;
QualType ArgType = Context.getTypeDeclType(ClassDecl);
+ if (Context.getLangOpts().OpenCLCPlusPlus)
+ ArgType = Context.getAddrSpaceQualType(ArgType, LangAS::opencl_generic);
QualType RetType = Context.getLValueReferenceType(ArgType);
bool Const = ClassDecl->implicitCopyAssignmentHasConstParam();
if (Const)
ArgType = ArgType.withConst();
- if (Context.getLangOpts().OpenCLCPlusPlus)
- ArgType = Context.getAddrSpaceQualType(ArgType, LangAS::opencl_generic);
-
ArgType = Context.getLValueReferenceType(ArgType);
bool Constexpr = defaultedSpecialMemberIsConstexpr(*this, ClassDecl,
@@ -11860,7 +11870,7 @@ CXXMethodDecl *Sema::DeclareImplicitCopyAssignment(CXXRecordDecl *ClassDecl) {
: ClassDecl->hasTrivialCopyAssignment());
// Note that we have added this copy-assignment operator.
- ++ASTContext::NumImplicitCopyAssignmentOperatorsDeclared;
+ ++getASTContext().NumImplicitCopyAssignmentOperatorsDeclared;
Scope *S = getScopeForContext(ClassDecl);
CheckImplicitSpecialMemberDeclaration(S, CopyAssignment);
@@ -12009,7 +12019,7 @@ void Sema::DefineImplicitCopyAssignment(SourceLocation CurrentLocation,
DerefBuilder DerefThis(This);
CastBuilder To(DerefThis,
Context.getQualifiedType(
- BaseType, CopyAssignOperator->getTypeQualifiers()),
+ BaseType, CopyAssignOperator->getMethodQualifiers()),
VK_LValue, BasePath);
// Build the copy.
@@ -12135,6 +12145,8 @@ CXXMethodDecl *Sema::DeclareImplicitMoveAssignment(CXXRecordDecl *ClassDecl) {
// constructor rules.
QualType ArgType = Context.getTypeDeclType(ClassDecl);
+ if (Context.getLangOpts().OpenCLCPlusPlus)
+ ArgType = Context.getAddrSpaceQualType(ArgType, LangAS::opencl_generic);
QualType RetType = Context.getLValueReferenceType(ArgType);
ArgType = Context.getRValueReferenceType(ArgType);
@@ -12181,7 +12193,7 @@ CXXMethodDecl *Sema::DeclareImplicitMoveAssignment(CXXRecordDecl *ClassDecl) {
: ClassDecl->hasTrivialMoveAssignment());
// Note that we have added this copy-assignment operator.
- ++ASTContext::NumImplicitMoveAssignmentOperatorsDeclared;
+ ++getASTContext().NumImplicitMoveAssignmentOperatorsDeclared;
Scope *S = getScopeForContext(ClassDecl);
CheckImplicitSpecialMemberDeclaration(S, MoveAssignment);
@@ -12374,7 +12386,7 @@ void Sema::DefineImplicitMoveAssignment(SourceLocation CurrentLocation,
// Implicitly cast "this" to the appropriately-qualified base type.
CastBuilder To(DerefThis,
Context.getQualifiedType(
- BaseType, MoveAssignOperator->getTypeQualifiers()),
+ BaseType, MoveAssignOperator->getMethodQualifiers()),
VK_LValue, BasePath);
// Build the move.
@@ -12564,7 +12576,7 @@ CXXConstructorDecl *Sema::DeclareImplicitCopyConstructor(
: ClassDecl->hasTrivialCopyConstructorForCall()));
// Note that we have declared this constructor.
- ++ASTContext::NumImplicitCopyConstructorsDeclared;
+ ++getASTContext().NumImplicitCopyConstructorsDeclared;
Scope *S = getScopeForContext(ClassDecl);
CheckImplicitSpecialMemberDeclaration(S, CopyConstructor);
@@ -12694,7 +12706,7 @@ CXXConstructorDecl *Sema::DeclareImplicitMoveConstructor(
: ClassDecl->hasTrivialMoveConstructorForCall()));
// Note that we have declared this constructor.
- ++ASTContext::NumImplicitMoveConstructorsDeclared;
+ ++getASTContext().NumImplicitMoveConstructorsDeclared;
Scope *S = getScopeForContext(ClassDecl);
CheckImplicitSpecialMemberDeclaration(S, MoveConstructor);