1616
1717#include " swift/Parse/Parser.h"
1818#include " swift/AST/ASTWalker.h"
19+ #include " swift/AST/Attr.h"
1920#include " swift/AST/DiagnosticsParse.h"
2021#include " swift/AST/TypeRepr.h"
2122#include " swift/Basic/EditorPlaceholder.h"
@@ -2335,6 +2336,7 @@ static void printTupleNames(const TypeRepr *typeRepr, llvm::raw_ostream &OS) {
23352336}
23362337
23372338ParserStatus Parser::parseClosureSignatureIfPresent (
2339+ DeclAttributes &attributes,
23382340 SourceRange &bracketRange,
23392341 SmallVectorImpl<CaptureListEntry> &captureList,
23402342 VarDecl *&capturedSelfDecl,
@@ -2344,6 +2346,7 @@ ParserStatus Parser::parseClosureSignatureIfPresent(
23442346 TypeExpr *&explicitResultType, SourceLoc &inLoc) {
23452347 // Clear out result parameters.
23462348 bracketRange = SourceRange ();
2349+ attributes = DeclAttributes ();
23472350 capturedSelfDecl = nullptr ;
23482351 params = nullptr ;
23492352 throwsLoc = SourceLoc ();
@@ -2360,9 +2363,16 @@ ParserStatus Parser::parseClosureSignatureIfPresent(
23602363
23612364 // If we have a leading token that may be part of the closure signature, do a
23622365 // speculative parse to validate it and look for 'in'.
2363- if (Tok.isAny (tok::l_paren, tok::l_square, tok::identifier, tok::kw__)) {
2366+ if (Tok.isAny (
2367+ tok::at_sign, tok::l_paren, tok::l_square, tok::identifier,
2368+ tok::kw__)) {
23642369 BacktrackingScope backtrack (*this );
23652370
2371+ // Consume attributes.
2372+ while (Tok.is (tok::at_sign)) {
2373+ skipAnyAttribute ();
2374+ }
2375+
23662376 // Skip by a closure capture list if present.
23672377 if (consumeIf (tok::l_square)) {
23682378 skipUntil (tok::r_square);
@@ -2425,6 +2435,9 @@ ParserStatus Parser::parseClosureSignatureIfPresent(
24252435 }
24262436 ParserStatus status;
24272437 SyntaxParsingContext ClosureSigCtx (SyntaxContext, SyntaxKind::ClosureSignature);
2438+
2439+ (void )parseDeclAttributeList (attributes);
2440+
24282441 if (Tok.is (tok::l_square) && peekToken ().is (tok::r_square)) {
24292442
24302443 SyntaxParsingContext CaptureCtx (SyntaxContext,
@@ -2721,6 +2734,7 @@ ParserResult<Expr> Parser::parseExprClosure() {
27212734 SourceLoc leftBrace = consumeToken ();
27222735
27232736 // Parse the closure-signature, if present.
2737+ DeclAttributes attributes;
27242738 SourceRange bracketRange;
27252739 SmallVector<CaptureListEntry, 2 > captureList;
27262740 VarDecl *capturedSelfDecl;
@@ -2731,8 +2745,8 @@ ParserResult<Expr> Parser::parseExprClosure() {
27312745 TypeExpr *explicitResultType;
27322746 SourceLoc inLoc;
27332747 Status |= parseClosureSignatureIfPresent (
2734- bracketRange, captureList, capturedSelfDecl, params, asyncLoc, throwsLoc ,
2735- arrowLoc, explicitResultType, inLoc);
2748+ attributes, bracketRange, captureList, capturedSelfDecl, params, asyncLoc,
2749+ throwsLoc, arrowLoc, explicitResultType, inLoc);
27362750
27372751 // If the closure was created in the context of an array type signature's
27382752 // size expression, there will not be a local context. A parse error will
@@ -2748,8 +2762,8 @@ ParserResult<Expr> Parser::parseExprClosure() {
27482762
27492763 // Create the closure expression and enter its context.
27502764 auto *closure = new (Context) ClosureExpr (
2751- bracketRange, capturedSelfDecl, params, asyncLoc, throwsLoc, arrowLoc ,
2752- inLoc, explicitResultType, discriminator, CurDeclContext);
2765+ attributes, bracketRange, capturedSelfDecl, params, asyncLoc, throwsLoc,
2766+ arrowLoc, inLoc, explicitResultType, discriminator, CurDeclContext);
27532767 ParseFunctionBody cc (*this , closure);
27542768
27552769 // Handle parameters.
0 commit comments