From 9be594e36d5961b5acd0aca69e3594d3a4c67bf4 Mon Sep 17 00:00:00 2001 From: Richard Smith Date: Thu, 22 Oct 2015 05:12:22 +0000 Subject: [PATCH] [coroutines] Add overloaded unary 'operator co_await'. llvm-svn: 250991 --- clang/include/clang/Basic/OperatorKinds.def | 1 + clang/lib/AST/ItaniumMangle.cpp | 3 +++ clang/lib/AST/MicrosoftMangle.cpp | 8 ++++++++ clang/lib/AST/StmtProfile.cpp | 1 + clang/lib/Sema/SemaOpenMP.cpp | 1 + clang/lib/Sema/SemaOverload.cpp | 1 + clang/test/Parser/cxx1z-coroutines.cpp | 14 ++++++++++++++ 7 files changed, 29 insertions(+) diff --git a/clang/include/clang/Basic/OperatorKinds.def b/clang/include/clang/Basic/OperatorKinds.def index d011e9d39ff8..34ad7644cd2b 100644 --- a/clang/include/clang/Basic/OperatorKinds.def +++ b/clang/include/clang/Basic/OperatorKinds.def @@ -101,6 +101,7 @@ OVERLOADED_OPERATOR_MULTI(Subscript , "[]" , false, t // ?: can *not* be overloaded, but we need the overload // resolution machinery for it. OVERLOADED_OPERATOR_MULTI(Conditional , "?" , false, true , false) +OVERLOADED_OPERATOR(Coawait , "co_await", kw_co_await , true , false, false) #undef OVERLOADED_OPERATOR_MULTI #undef OVERLOADED_OPERATOR diff --git a/clang/lib/AST/ItaniumMangle.cpp b/clang/lib/AST/ItaniumMangle.cpp index 64f9ccd99673..86bc8e67756d 100644 --- a/clang/lib/AST/ItaniumMangle.cpp +++ b/clang/lib/AST/ItaniumMangle.cpp @@ -1753,6 +1753,9 @@ CXXNameMangler::mangleOperatorName(OverloadedOperatorKind OO, unsigned Arity) { // The conditional operator can't be overloaded, but we still handle it when // mangling expressions. case OO_Conditional: Out << "qu"; break; + // Proposal on cxx-abi-dev, 2015-10-21. + // ::= aw # co_await + case OO_Coawait: Out << "aw"; break; case OO_None: case NUM_OVERLOADED_OPERATORS: diff --git a/clang/lib/AST/MicrosoftMangle.cpp b/clang/lib/AST/MicrosoftMangle.cpp index 9d6c7dc64f8c..c4baed21cb43 100644 --- a/clang/lib/AST/MicrosoftMangle.cpp +++ b/clang/lib/AST/MicrosoftMangle.cpp @@ -1046,6 +1046,14 @@ void MicrosoftCXXNameMangler::mangleOperatorName(OverloadedOperatorKind OO, break; } + case OO_Coawait: { + DiagnosticsEngine &Diags = Context.getDiags(); + unsigned DiagID = Diags.getCustomDiagID(DiagnosticsEngine::Error, + "cannot mangle this operator co_await yet"); + Diags.Report(Loc, DiagID); + break; + } + case OO_None: case NUM_OVERLOADED_OPERATORS: llvm_unreachable("Not an overloaded operator"); diff --git a/clang/lib/AST/StmtProfile.cpp b/clang/lib/AST/StmtProfile.cpp index cf5289adc2c3..93b80e5d99cb 100644 --- a/clang/lib/AST/StmtProfile.cpp +++ b/clang/lib/AST/StmtProfile.cpp @@ -854,6 +854,7 @@ static Stmt::StmtClass DecodeOperatorCall(const CXXOperatorCallExpr *S, case OO_Arrow: case OO_Call: case OO_Conditional: + case OO_Coawait: case NUM_OVERLOADED_OPERATORS: llvm_unreachable("Invalid operator call kind"); diff --git a/clang/lib/Sema/SemaOpenMP.cpp b/clang/lib/Sema/SemaOpenMP.cpp index c4e1b26e7c5f..705e6f5ef0a3 100644 --- a/clang/lib/Sema/SemaOpenMP.cpp +++ b/clang/lib/Sema/SemaOpenMP.cpp @@ -6385,6 +6385,7 @@ OMPClause *Sema::ActOnOpenMPReductionClause( case OO_Call: case OO_Subscript: case OO_Conditional: + case OO_Coawait: case NUM_OVERLOADED_OPERATORS: llvm_unreachable("Unexpected reduction identifier"); case OO_None: diff --git a/clang/lib/Sema/SemaOverload.cpp b/clang/lib/Sema/SemaOverload.cpp index 743ca680427c..d4a220037ec5 100644 --- a/clang/lib/Sema/SemaOverload.cpp +++ b/clang/lib/Sema/SemaOverload.cpp @@ -8228,6 +8228,7 @@ void Sema::AddBuiltinOperatorCandidates(OverloadedOperatorKind Op, case OO_Array_New: case OO_Array_Delete: case OO_Call: + case OO_Coawait: llvm_unreachable( "Special operators don't use AddBuiltinOperatorCandidates"); diff --git a/clang/test/Parser/cxx1z-coroutines.cpp b/clang/test/Parser/cxx1z-coroutines.cpp index 266337634e96..3e698404a600 100644 --- a/clang/test/Parser/cxx1z-coroutines.cpp +++ b/clang/test/Parser/cxx1z-coroutines.cpp @@ -19,3 +19,17 @@ U f(T t) { else co_return {t}; } + +struct Y {}; +struct X { Y operator co_await(); }; +struct Z {}; +Y operator co_await(Z); + +void f(X x, Z z) { + x.operator co_await(); + operator co_await(z); +} + +void operator co_await(); // expected-error {{must have at least one parameter}} +void operator co_await(X, Y, Z); // expected-error {{must be a unary operator}} +void operator co_await(int); // expected-error {{parameter of class or enumeration type}}