summaryrefslogtreecommitdiffstats
path: root/clang/lib/Sema/SemaDeclCXX.cpp
diff options
context:
space:
mode:
authorRichard Smith <richard@metafoo.co.uk>2019-12-10 19:50:26 -0800
committerRichard Smith <richard@metafoo.co.uk>2019-12-10 19:54:35 -0800
commitffe612922cb5aa2767c79d47a1b162811a08583f (patch)
tree6bb9a155e5dc06a24077030144c19aa624231854 /clang/lib/Sema/SemaDeclCXX.cpp
parent8e0c9e21bf5f3e7a427b07e3eaf3bc80d2c74cb6 (diff)
downloadbcm5719-llvm-ffe612922cb5aa2767c79d47a1b162811a08583f.tar.gz
bcm5719-llvm-ffe612922cb5aa2767c79d47a1b162811a08583f.zip
[c++20] Implement P1946R0: allow defaulted comparisons to take their
arguments by value.
Diffstat (limited to 'clang/lib/Sema/SemaDeclCXX.cpp')
-rw-r--r--clang/lib/Sema/SemaDeclCXX.cpp31
1 files changed, 25 insertions, 6 deletions
diff --git a/clang/lib/Sema/SemaDeclCXX.cpp b/clang/lib/Sema/SemaDeclCXX.cpp
index 36528609769..5373bb422ad 100644
--- a/clang/lib/Sema/SemaDeclCXX.cpp
+++ b/clang/lib/Sema/SemaDeclCXX.cpp
@@ -7921,22 +7921,41 @@ bool Sema::CheckExplicitlyDefaultedComparison(Scope *S, FunctionDecl *FD,
// non-template function declared in the member-specification of C that is
// -- a non-static const member of C having one parameter of type
// const C&, or
- // -- a friend of C having two parameters of type const C&.
- QualType ExpectedParmType =
- Context.getLValueReferenceType(Context.getRecordType(RD).withConst());
+ // -- a friend of C having two parameters of type const C& or two
+ // parameters of type C.
+ QualType ExpectedParmType1 = Context.getRecordType(RD);
+ QualType ExpectedParmType2 =
+ Context.getLValueReferenceType(ExpectedParmType1.withConst());
+ if (isa<CXXMethodDecl>(FD))
+ ExpectedParmType1 = ExpectedParmType2;
for (const ParmVarDecl *Param : FD->parameters()) {
if (!Param->getType()->isDependentType() &&
- !Context.hasSameType(Param->getType(), ExpectedParmType)) {
+ !Context.hasSameType(Param->getType(), ExpectedParmType1) &&
+ !Context.hasSameType(Param->getType(), ExpectedParmType2)) {
// Don't diagnose an implicit 'operator=='; we will have diagnosed the
// corresponding defaulted 'operator<=>' already.
if (!FD->isImplicit()) {
Diag(FD->getLocation(), diag::err_defaulted_comparison_param)
- << (int)DCK << Param->getType() << ExpectedParmType
- << Param->getSourceRange();
+ << (int)DCK << Param->getType() << ExpectedParmType1
+ << !isa<CXXMethodDecl>(FD)
+ << ExpectedParmType2 << Param->getSourceRange();
}
return true;
}
}
+ if (FD->getNumParams() == 2 &&
+ !Context.hasSameType(FD->getParamDecl(0)->getType(),
+ FD->getParamDecl(1)->getType())) {
+ if (!FD->isImplicit()) {
+ Diag(FD->getLocation(), diag::err_defaulted_comparison_param_mismatch)
+ << (int)DCK
+ << FD->getParamDecl(0)->getType()
+ << FD->getParamDecl(0)->getSourceRange()
+ << FD->getParamDecl(1)->getType()
+ << FD->getParamDecl(1)->getSourceRange();
+ }
+ return true;
+ }
// ... non-static const member ...
if (auto *MD = dyn_cast<CXXMethodDecl>(FD)) {
OpenPOWER on IntegriCloud