Skip to content

Commit 3c11671

Browse files
authored
Merge pull request #969 from DougGregor/syntactic-macro-system
2 parents be959d1 + 5c02eb5 commit 3c11671

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

49 files changed

+2970
-224
lines changed

CodeGeneration/Sources/SyntaxSupport/gyb_generated/DeclNodes.swift

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1500,4 +1500,43 @@ public let DECL_NODES: [Node] = [
15001500
])
15011501
]),
15021502

1503+
Node(name: "MacroExpansionDecl",
1504+
nameForDiagnostics: "pound literal declaration",
1505+
kind: "Decl",
1506+
children: [
1507+
Child(name: "PoundToken",
1508+
kind: "PoundToken",
1509+
description: "The `#` sign.",
1510+
tokenChoices: [
1511+
"Pound"
1512+
]),
1513+
Child(name: "Macro",
1514+
kind: "IdentifierToken",
1515+
tokenChoices: [
1516+
"Identifier"
1517+
]),
1518+
Child(name: "LeftParen",
1519+
kind: "LeftParenToken",
1520+
isOptional: true,
1521+
tokenChoices: [
1522+
"LeftParen"
1523+
]),
1524+
Child(name: "ArgumentList",
1525+
kind: "TupleExprElementList",
1526+
collectionElementName: "Argument"),
1527+
Child(name: "RightParen",
1528+
kind: "RightParenToken",
1529+
isOptional: true,
1530+
tokenChoices: [
1531+
"RightParen"
1532+
]),
1533+
Child(name: "TrailingClosure",
1534+
kind: "ClosureExpr",
1535+
isOptional: true),
1536+
Child(name: "AdditionalTrailingClosures",
1537+
kind: "MultipleTrailingClosureElementList",
1538+
isOptional: true,
1539+
collectionElementName: "AdditionalTrailingClosure")
1540+
]),
1541+
15031542
]

CodeGeneration/Sources/SyntaxSupport/gyb_generated/ExprNodes.swift

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1288,6 +1288,45 @@ public let EXPR_NODES: [Node] = [
12881288
])
12891289
]),
12901290

1291+
Node(name: "MacroExpansionExpr",
1292+
nameForDiagnostics: "pound literal expression",
1293+
kind: "Expr",
1294+
children: [
1295+
Child(name: "PoundToken",
1296+
kind: "PoundToken",
1297+
description: "The `#` sign.",
1298+
tokenChoices: [
1299+
"Pound"
1300+
]),
1301+
Child(name: "Macro",
1302+
kind: "IdentifierToken",
1303+
tokenChoices: [
1304+
"Identifier"
1305+
]),
1306+
Child(name: "LeftParen",
1307+
kind: "LeftParenToken",
1308+
isOptional: true,
1309+
tokenChoices: [
1310+
"LeftParen"
1311+
]),
1312+
Child(name: "ArgumentList",
1313+
kind: "TupleExprElementList",
1314+
collectionElementName: "Argument"),
1315+
Child(name: "RightParen",
1316+
kind: "RightParenToken",
1317+
isOptional: true,
1318+
tokenChoices: [
1319+
"RightParen"
1320+
]),
1321+
Child(name: "TrailingClosure",
1322+
kind: "ClosureExpr",
1323+
isOptional: true),
1324+
Child(name: "AdditionalTrailingClosures",
1325+
kind: "MultipleTrailingClosureElementList",
1326+
isOptional: true,
1327+
collectionElementName: "AdditionalTrailingClosure")
1328+
]),
1329+
12911330
Node(name: "PostfixIfConfigExpr",
12921331
nameForDiagnostics: nil,
12931332
kind: "Expr",

CodeGeneration/Sources/SyntaxSupport/gyb_generated/NodeSerializationCodes.swift

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -296,4 +296,6 @@ public let SYNTAX_NODE_SERIALIZATION_CODES: [String: Int] = [
296296
"KeyPathComponentList": 285,
297297
"KeyPathComponent": 286,
298298
"OldKeyPathExpr": 287,
299+
"MacroExpansionExpr": 288,
300+
"MacroExpansionDecl": 289,
299301
]

Package.swift

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,7 @@ let package = Package(
5050
.library(name: "SwiftSyntax", type: .static, targets: ["SwiftSyntax"]),
5151
.library(name: "SwiftSyntaxParser", type: .static, targets: ["SwiftSyntaxParser"]),
5252
.library(name: "SwiftSyntaxBuilder", type: .static, targets: ["SwiftSyntaxBuilder"]),
53+
.library(name: "_SwiftSyntaxMacros", type: .static, targets: ["_SwiftSyntaxMacros"]),
5354
],
5455
targets: [
5556
.target(
@@ -140,13 +141,21 @@ let package = Package(
140141
"SwiftCompilerSupport.h"
141142
]
142143
),
144+
.target(
145+
name: "_SwiftSyntaxMacros",
146+
dependencies: [
147+
"SwiftSyntax", "SwiftSyntaxBuilder", "SwiftParser", "SwiftDiagnostics"
148+
],
149+
exclude: [
150+
"CMakeLists.txt",
151+
]),
143152
.executableTarget(
144153
name: "lit-test-helper",
145154
dependencies: ["SwiftSyntax", "SwiftSyntaxParser"]
146155
),
147156
.executableTarget(
148157
name: "swift-parser-cli",
149-
dependencies: ["SwiftDiagnostics", "SwiftSyntax", "SwiftParser", "SwiftOperators",
158+
dependencies: ["SwiftDiagnostics", "SwiftSyntax", "SwiftParser", "SwiftOperators", "_SwiftSyntaxMacros",
150159
.product(name: "ArgumentParser", package: "swift-argument-parser")]
151160
),
152161
.testTarget(
@@ -166,6 +175,12 @@ let package = Package(
166175
dependencies: ["SwiftSyntaxParser", "_SwiftSyntaxTestSupport"],
167176
exclude: ["Inputs"]
168177
),
178+
.testTarget(
179+
name: "SwiftSyntaxMacrosTest",
180+
dependencies: ["SwiftDiagnostics", "SwiftOperators", "SwiftParser",
181+
"_SwiftSyntaxTestSupport", "SwiftSyntaxBuilder",
182+
"_SwiftSyntaxMacros"]
183+
),
169184
.testTarget(
170185
name: "PerformanceTest",
171186
dependencies: ["SwiftSyntax", "SwiftSyntaxParser", "SwiftParser"],

Sources/SwiftBasicFormat/generated/BasicFormat.swift

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -806,6 +806,24 @@ open class BasicFormat: SyntaxRewriter {
806806
return ExprSyntax(ObjcSelectorExprSyntax(unexpectedBeforePoundSelector, poundSelector: poundSelector, unexpectedBetweenPoundSelectorAndLeftParen, leftParen: leftParen, unexpectedBetweenLeftParenAndKind, kind: kind, unexpectedBetweenKindAndColon, colon: colon, unexpectedBetweenColonAndName, name: name, unexpectedBetweenNameAndRightParen, rightParen: rightParen))
807807
}
808808

809+
open override func visit(_ node: MacroExpansionExprSyntax) -> ExprSyntax {
810+
let unexpectedBeforePoundToken = node.unexpectedBeforePoundToken.map(self.visit)?.cast(UnexpectedNodesSyntax.self)
811+
let poundToken = self.visit(node.poundToken).cast(TokenSyntax.self)
812+
let unexpectedBetweenPoundTokenAndMacro = node.unexpectedBetweenPoundTokenAndMacro.map(self.visit)?.cast(UnexpectedNodesSyntax.self)
813+
let macro = self.visit(node.macro).cast(TokenSyntax.self)
814+
let unexpectedBetweenMacroAndLeftParen = node.unexpectedBetweenMacroAndLeftParen.map(self.visit)?.cast(UnexpectedNodesSyntax.self)
815+
let leftParen = node.leftParen.map(self.visit)?.cast(TokenSyntax.self)
816+
let unexpectedBetweenLeftParenAndArgumentList = node.unexpectedBetweenLeftParenAndArgumentList.map(self.visit)?.cast(UnexpectedNodesSyntax.self)
817+
let argumentList = self.visit(node.argumentList).cast(TupleExprElementListSyntax.self)
818+
let unexpectedBetweenArgumentListAndRightParen = node.unexpectedBetweenArgumentListAndRightParen.map(self.visit)?.cast(UnexpectedNodesSyntax.self)
819+
let rightParen = node.rightParen.map(self.visit)?.cast(TokenSyntax.self)
820+
let unexpectedBetweenRightParenAndTrailingClosure = node.unexpectedBetweenRightParenAndTrailingClosure.map(self.visit)?.cast(UnexpectedNodesSyntax.self)
821+
let trailingClosure = node.trailingClosure.map(self.visit)?.cast(ClosureExprSyntax.self)
822+
let unexpectedBetweenTrailingClosureAndAdditionalTrailingClosures = node.unexpectedBetweenTrailingClosureAndAdditionalTrailingClosures.map(self.visit)?.cast(UnexpectedNodesSyntax.self)
823+
let additionalTrailingClosures = node.additionalTrailingClosures.map(self.visit)?.cast(MultipleTrailingClosureElementListSyntax.self)
824+
return ExprSyntax(MacroExpansionExprSyntax(unexpectedBeforePoundToken, poundToken: poundToken, unexpectedBetweenPoundTokenAndMacro, macro: macro, unexpectedBetweenMacroAndLeftParen, leftParen: leftParen, unexpectedBetweenLeftParenAndArgumentList, argumentList: argumentList, unexpectedBetweenArgumentListAndRightParen, rightParen: rightParen, unexpectedBetweenRightParenAndTrailingClosure, trailingClosure: trailingClosure, unexpectedBetweenTrailingClosureAndAdditionalTrailingClosures, additionalTrailingClosures: additionalTrailingClosures))
825+
}
826+
809827
open override func visit(_ node: PostfixIfConfigExprSyntax) -> ExprSyntax {
810828
let unexpectedBeforeBase = node.unexpectedBeforeBase.map(self.visit)?.cast(UnexpectedNodesSyntax.self)
811829
let base = node.base.map(self.visit)?.cast(ExprSyntax.self)
@@ -1575,6 +1593,24 @@ open class BasicFormat: SyntaxRewriter {
15751593
return Syntax(PrecedenceGroupAssociativitySyntax(unexpectedBeforeAssociativityKeyword, associativityKeyword: associativityKeyword, unexpectedBetweenAssociativityKeywordAndColon, colon: colon, unexpectedBetweenColonAndValue, value: value))
15761594
}
15771595

1596+
open override func visit(_ node: MacroExpansionDeclSyntax) -> DeclSyntax {
1597+
let unexpectedBeforePoundToken = node.unexpectedBeforePoundToken.map(self.visit)?.cast(UnexpectedNodesSyntax.self)
1598+
let poundToken = self.visit(node.poundToken).cast(TokenSyntax.self)
1599+
let unexpectedBetweenPoundTokenAndMacro = node.unexpectedBetweenPoundTokenAndMacro.map(self.visit)?.cast(UnexpectedNodesSyntax.self)
1600+
let macro = self.visit(node.macro).cast(TokenSyntax.self)
1601+
let unexpectedBetweenMacroAndLeftParen = node.unexpectedBetweenMacroAndLeftParen.map(self.visit)?.cast(UnexpectedNodesSyntax.self)
1602+
let leftParen = node.leftParen.map(self.visit)?.cast(TokenSyntax.self)
1603+
let unexpectedBetweenLeftParenAndArgumentList = node.unexpectedBetweenLeftParenAndArgumentList.map(self.visit)?.cast(UnexpectedNodesSyntax.self)
1604+
let argumentList = self.visit(node.argumentList).cast(TupleExprElementListSyntax.self)
1605+
let unexpectedBetweenArgumentListAndRightParen = node.unexpectedBetweenArgumentListAndRightParen.map(self.visit)?.cast(UnexpectedNodesSyntax.self)
1606+
let rightParen = node.rightParen.map(self.visit)?.cast(TokenSyntax.self)
1607+
let unexpectedBetweenRightParenAndTrailingClosure = node.unexpectedBetweenRightParenAndTrailingClosure.map(self.visit)?.cast(UnexpectedNodesSyntax.self)
1608+
let trailingClosure = node.trailingClosure.map(self.visit)?.cast(ClosureExprSyntax.self)
1609+
let unexpectedBetweenTrailingClosureAndAdditionalTrailingClosures = node.unexpectedBetweenTrailingClosureAndAdditionalTrailingClosures.map(self.visit)?.cast(UnexpectedNodesSyntax.self)
1610+
let additionalTrailingClosures = node.additionalTrailingClosures.map(self.visit)?.cast(MultipleTrailingClosureElementListSyntax.self)
1611+
return DeclSyntax(MacroExpansionDeclSyntax(unexpectedBeforePoundToken, poundToken: poundToken, unexpectedBetweenPoundTokenAndMacro, macro: macro, unexpectedBetweenMacroAndLeftParen, leftParen: leftParen, unexpectedBetweenLeftParenAndArgumentList, argumentList: argumentList, unexpectedBetweenArgumentListAndRightParen, rightParen: rightParen, unexpectedBetweenRightParenAndTrailingClosure, trailingClosure: trailingClosure, unexpectedBetweenTrailingClosureAndAdditionalTrailingClosures, additionalTrailingClosures: additionalTrailingClosures))
1612+
}
1613+
15781614
open override func visit(_ node: TokenListSyntax) -> Syntax {
15791615
let formattedChildren = node.children(viewMode: .all).map {
15801616
self.visit($0).cast(TokenSyntax.self)

Sources/SwiftParser/Declarations.swift

Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -169,6 +169,8 @@ extension Parser {
169169
return RawDeclSyntax(directive)
170170
case (.poundWarningKeyword, _)?, (.poundErrorKeyword, _)?:
171171
return self.parsePoundDiagnosticDeclaration()
172+
case (.pound, _)?:
173+
return RawDeclSyntax(self.parseMacroExpansionDeclaration())
172174
case nil:
173175
break
174176
}
@@ -2336,4 +2338,57 @@ extension Parser {
23362338
arena: self.arena))
23372339
}
23382340
}
2341+
2342+
/// Parse a macro expansion as an declaration.
2343+
///
2344+
///
2345+
/// Grammar
2346+
/// =======
2347+
///
2348+
/// macro-expansion-declaration → '#' identifier expr-call-suffix?
2349+
mutating func parseMacroExpansionDeclaration() -> RawMacroExpansionDeclSyntax {
2350+
let poundKeyword = self.consumeAnyToken()
2351+
let (unexpectedBeforeMacro, macro) = self.expectIdentifier()
2352+
2353+
// Parse the optional parenthesized argument list.
2354+
let leftParen = self.consume(if: .leftParen, where: { !$0.isAtStartOfLine })
2355+
let args: [RawTupleExprElementSyntax]
2356+
let unexpectedBeforeRightParen: RawUnexpectedNodesSyntax?
2357+
let rightParen: RawTokenSyntax?
2358+
if leftParen != nil {
2359+
args = parseArgumentListElements(pattern: .none)
2360+
(unexpectedBeforeRightParen, rightParen) = self.expect(.rightParen)
2361+
} else {
2362+
args = []
2363+
unexpectedBeforeRightParen = nil
2364+
rightParen = nil
2365+
}
2366+
2367+
// Parse the optional trailing closures.
2368+
let trailingClosure: RawClosureExprSyntax?
2369+
let additionalTrailingClosures: RawMultipleTrailingClosureElementListSyntax?
2370+
if self.at(.leftBrace),
2371+
self.lookahead().isValidTrailingClosure(.trailingClosure) {
2372+
(trailingClosure, additionalTrailingClosures) =
2373+
self.parseTrailingClosures(.trailingClosure)
2374+
} else {
2375+
trailingClosure = nil
2376+
additionalTrailingClosures = nil
2377+
}
2378+
2379+
return RawMacroExpansionDeclSyntax(
2380+
poundToken: poundKeyword,
2381+
unexpectedBeforeMacro,
2382+
macro: macro,
2383+
leftParen: leftParen,
2384+
argumentList: RawTupleExprElementListSyntax(
2385+
elements: args, arena: self.arena
2386+
),
2387+
unexpectedBeforeRightParen,
2388+
rightParen: rightParen,
2389+
trailingClosure: trailingClosure,
2390+
additionalTrailingClosures: additionalTrailingClosures,
2391+
arena: self.arena
2392+
)
2393+
}
23392394
}

Sources/SwiftParser/Directives.swift

Lines changed: 0 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -123,22 +123,6 @@ extension Parser {
123123
}
124124

125125
extension Parser {
126-
/// Parse a #line literal.
127-
///
128-
/// Grammar
129-
/// =======
130-
///
131-
/// literal-expression → '#line'
132-
@_spi(RawSyntax)
133-
public mutating func parsePoundLineDirective() -> RawPoundLineExprSyntax {
134-
let (unexpectedBeforeToken, token) = self.expect(.poundLineKeyword)
135-
return RawPoundLineExprSyntax(
136-
unexpectedBeforeToken,
137-
poundLine: token,
138-
arena: self.arena
139-
)
140-
}
141-
142126
/// Parse a line control directive.
143127
///
144128
/// Grammar

0 commit comments

Comments
 (0)