Skip to content

Cherry-pick multiple PRs to release/5.9 #1556

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 22 commits into from
Apr 22, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
22 commits
Select commit Hold shift + click to select a range
fca27eb
Merge pull request #1490 from ahoppen/ahoppen/trivia-invalid-utf8
ahoppen Apr 5, 2023
2772089
Merge pull request #1497 from andrewjl/andrewjl/fix-xctskip-warning
ahoppen Apr 6, 2023
f89e946
Merge pull request #1482 from ahoppen/ahoppen/swiftsyntax-public-api
ahoppen Apr 11, 2023
5ee8d66
Merge pull request #1519 from kimdv/kimdv/fix-warning
ahoppen Apr 12, 2023
db9347b
Merge pull request #1520 from kishikawakatsumi/string-literal-escape
ahoppen Apr 12, 2023
794d651
Merge pull request #1454 from StevenWong12/effectful_properties_diagn…
ahoppen Apr 12, 2023
b6099e9
Merge pull request #1518 from stevapple/else-spacing
ahoppen Apr 12, 2023
f430866
Merge pull request #1527 from ahoppen/ahoppen/documentation-for-initi…
ahoppen Apr 13, 2023
a663fbb
Merge pull request #1517 from stevapple/fix-for-in
ahoppen Apr 13, 2023
a017406
Merge pull request #1466 from ahoppen/ahoppen/rawsyntaxvalidation
ahoppen Apr 13, 2023
deb6d66
Merge pull request #1503 from ahoppen/ahoppen/better-debug-description
ahoppen Apr 13, 2023
c5ffdb7
Merge pull request #1537 from ahoppen/ahoppen/rawsyntaxtoken-validation
ahoppen Apr 14, 2023
2fc2f62
Merge pull request #1523 from ahoppen/ahoppen/readme
ahoppen Apr 14, 2023
a45c06e
Merge pull request #1526 from ahoppen/ahoppen/no-debug-guards
ahoppen Apr 14, 2023
b011378
Merge pull request #1524 from ahoppen/ahoppen/memberblock
ahoppen Apr 15, 2023
fe1d21d
Merge pull request #1538 from ahoppen/ahoppen/source-alteration-fixes
ahoppen Apr 18, 2023
6e8adda
Merge pull request #1541 from ahoppen/ahoppen/package-formatting
ahoppen Apr 15, 2023
c346d3a
Merge pull request #1539 from ahoppen/ahoppen/include-child-name-in-d…
ahoppen Apr 15, 2023
73f754a
Merge pull request #1552 from ahoppen/ahoppen/regen
ahoppen Apr 15, 2023
23c09ed
Merge pull request #1340 from ahoppen/ahoppen/source-alteration
ahoppen Apr 16, 2023
a577f19
Merge pull request #1544 from ahoppen/ahoppen/remove-swiftsyntaxparser
ahoppen Apr 17, 2023
8d68708
Re-generate code-generated files
ahoppen Apr 18, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 0 additions & 8 deletions BUILD.bazel
Original file line number Diff line number Diff line change
Expand Up @@ -95,14 +95,6 @@ swift_syntax_library(
],
)

swift_syntax_library(
name = "SwiftSyntaxParser",
deps = [
":SwiftParser",
":SwiftSyntax",
],
)

swift_syntax_library(
name = "SwiftRefactor",
deps = [
Expand Down
8 changes: 2 additions & 6 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -43,11 +43,7 @@ If you can’t find it in your Schemes, you need to manually add it using Produc

### XCTests

The `SwiftSyntaxParser` module (the legacy parser) of this repository depends on the C++ parser library (`_InternalSwiftSyntaxParser.dylib`) to parse source code.
The syntax node definitions of that parser library need to match those used by your SwiftSyntax checkout.
Most of the time, the parser library included in the latest Swift Development Snapshot will fulfill this requirement.

To run the tests in Xcode, select the latest Swift Development Snapshot in Xcode -> Toolchains, select the SwiftSyntax-Package scheme and hit Product -> Test.
To run the tests in Xcode, select the SwiftSyntax-Package scheme and hit Product -> Test.

You can also run the tests from the command line using
```bash
Expand All @@ -68,7 +64,7 @@ Tip: Running SwiftSyntax’s self-parse tests takes the majority of testing time

### `lit`-based tests

A few tests of the `SwiftSyntaxParser` module (the legacy parser), which test the interaction between SwiftSyntax and the C++ parser library (`_InternalSwiftSyntaxParser.dylib`) are based LLVM’s `lit` and `FileCheck` tools.
A few tests are based LLVM’s `lit` and `FileCheck` tools.
To run these, build `FileCheck`, e.g. by building the Swift compiler and run the tests using the following command:
```bash
./build-script.py test --toolchain /Library/Developer/Toolchains/swift-DEVELOPMENT-SNAPSHOT-<recent date>.xctoolchain/usr --skip-lit-tests --filecheck-exec /path/to/build/Release+Asserts/llvm-macosx-x86_64/bin/FileCheck
Expand Down
11 changes: 5 additions & 6 deletions CodeGeneration/Sources/SyntaxSupport/Classification.swift
Original file line number Diff line number Diff line change
Expand Up @@ -28,16 +28,15 @@ public class SyntaxClassification {
public class ChildClassification {
public let parent: Node
public let childIndex: Int
public let isToken: Bool
public let classification: SyntaxClassification?
public let force: Bool
public let child: Child
public var isToken: Bool { child.isToken }
public var classification: SyntaxClassification? { child.classification }
public var force: Bool { child.forceClassification }

public init(node: Node, childIndex: Int, child: Child) {
self.parent = node
self.childIndex = childIndex
self.isToken = child.syntaxKind.hasSuffix("Token")
self.classification = child.classification
self.force = child.forceClassification
self.child = child
}
}

Expand Down
26 changes: 24 additions & 2 deletions CodeGeneration/Sources/SyntaxSupport/CommonNodes.swift
Original file line number Diff line number Diff line change
Expand Up @@ -83,9 +83,31 @@ public let COMMON_NODES: [Node] = [
]
),

// decl-effect-specifiers -> (async | reasync)? (throws | rethrows)?
// accessor-effect-specifiers -> (async)? (throws)?
Node(
name: "DeclEffectSpecifiers",
name: "AccessorEffectSpecifiers",
nameForDiagnostics: "accessor specifiers",
kind: "Syntax",
traits: [
"EffectSpecifiers"
],
children: [
Child(
name: "AsyncSpecifier",
kind: .token(choices: [.keyword(text: "async")]),
isOptional: true
),
Child(
name: "ThrowsSpecifier",
kind: .token(choices: [.keyword(text: "throws")]),
isOptional: true
),
]
),

// funtion-effect-specifiers -> (async | reasync)? (throws | rethrows)?
Node(
name: "FunctionEffectSpecifiers",
nameForDiagnostics: "effect specifiers",
kind: "Syntax",
traits: [
Expand Down
81 changes: 68 additions & 13 deletions CodeGeneration/Sources/SyntaxSupport/DeclNodes.swift
Original file line number Diff line number Diff line change
Expand Up @@ -96,7 +96,7 @@ public let DECL_NODES: [Node] = [
),
Child(
name: "EffectSpecifiers",
kind: .node(kind: "DeclEffectSpecifiers"),
kind: .node(kind: "AccessorEffectSpecifiers"),
isOptional: true
),
Child(
Expand Down Expand Up @@ -196,7 +196,7 @@ public let DECL_NODES: [Node] = [
isOptional: true
),
Child(
name: "Members",
name: "MemberBlock",
kind: .node(kind: "MemberDeclBlock")
),
]
Expand Down Expand Up @@ -312,7 +312,7 @@ public let DECL_NODES: [Node] = [
isOptional: true
),
Child(
name: "Members",
name: "MemberBlock",
kind: .node(kind: "MemberDeclBlock")
),
]
Expand All @@ -332,7 +332,7 @@ public let DECL_NODES: [Node] = [
),
Child(
name: "Detail",
kind: .token(choices: [.token(tokenKind: "IdentifierToken"), .keyword(text: "set")])
kind: .token(choices: [.token(tokenKind: "IdentifierToken")])
),
Child(
name: "RightParen",
Expand All @@ -348,7 +348,44 @@ public let DECL_NODES: [Node] = [
children: [
Child(
name: "Name",
kind: .token(choices: [.keyword(text: "class"), .keyword(text: "convenience"), .keyword(text: "dynamic"), .keyword(text: "final"), .keyword(text: "infix"), .keyword(text: "lazy"), .keyword(text: "optional"), .keyword(text: "override"), .keyword(text: "postfix"), .keyword(text: "prefix"), .keyword(text: "required"), .keyword(text: "static"), .keyword(text: "unowned"), .keyword(text: "weak"), .keyword(text: "private"), .keyword(text: "fileprivate"), .keyword(text: "internal"), .keyword(text: "public"), .keyword(text: "open"), .keyword(text: "mutating"), .keyword(text: "nonmutating"), .keyword(text: "indirect"), .keyword(text: "__consuming"), .keyword(text: "borrowing"), .keyword(text: "consuming"), .keyword(text: "actor"), .keyword(text: "async"), .keyword(text: "distributed"), .keyword(text: "isolated"), .keyword(text: "nonisolated"), .keyword(text: "_const"), .keyword(text: "_local"), .keyword(text: "package")]),
kind: .token(choices: [
.keyword(text: "__consuming"),
.keyword(text: "__setter_access"),
.keyword(text: "_const"),
.keyword(text: "_local"),
.keyword(text: "actor"),
.keyword(text: "async"),
.keyword(text: "borrowing"),
.keyword(text: "class"),
.keyword(text: "consuming"),
.keyword(text: "convenience"),
.keyword(text: "distributed"),
.keyword(text: "dynamic"),
.keyword(text: "fileprivate"),
.keyword(text: "final"),
.keyword(text: "indirect"),
.keyword(text: "infix"),
.keyword(text: "internal"),
.keyword(text: "isolated"),
.keyword(text: "lazy"),
.keyword(text: "mutating"),
.keyword(text: "nonisolated"),
.keyword(text: "nonmutating"),
.keyword(text: "open"),
.keyword(text: "optional"),
.keyword(text: "override"),
.keyword(text: "package"),
.keyword(text: "postfix"),
.keyword(text: "prefix"),
.keyword(text: "private"),
.keyword(text: "public"),
.keyword(text: "reasync"),
.keyword(text: "required"),
.keyword(text: "setter_access"),
.keyword(text: "static"),
.keyword(text: "unowned"),
.keyword(text: "weak"),
]),
classification: "Attribute"
),
Child(
Expand Down Expand Up @@ -654,7 +691,7 @@ public let DECL_NODES: [Node] = [
isOptional: true
),
Child(
name: "Members",
name: "MemberBlock",
kind: .node(kind: "MemberDeclBlock"),
description: "The cases and other members of this enum."
),
Expand Down Expand Up @@ -709,7 +746,7 @@ public let DECL_NODES: [Node] = [
isOptional: true
),
Child(
name: "Members",
name: "MemberBlock",
kind: .node(kind: "MemberDeclBlock")
),
]
Expand Down Expand Up @@ -842,7 +879,7 @@ public let DECL_NODES: [Node] = [
),

// function-signature ->
// '(' parameter-list? ')' decl-effect-specifiers? return-clause?
// '(' parameter-list? ')' function-effect-specifiers? return-clause?
Node(
name: "FunctionSignature",
nameForDiagnostics: "function signature",
Expand All @@ -854,7 +891,7 @@ public let DECL_NODES: [Node] = [
),
Child(
name: "EffectSpecifiers",
kind: .node(kind: "DeclEffectSpecifiers"),
kind: .node(kind: "FunctionEffectSpecifiers"),
isOptional: true
),
Child(
Expand Down Expand Up @@ -1024,6 +1061,16 @@ public let DECL_NODES: [Node] = [
Node(
name: "InitializerDecl",
nameForDiagnostics: "initializer",
description: """
An initializer declaration like the following.

```swift
init(someParameter: Int) {
}
```

The body is optional because this node also represents initializer requirements inside protocols.
""",
kind: "Decl",
traits: [
"Attributed"
Expand All @@ -1033,43 +1080,51 @@ public let DECL_NODES: [Node] = [
name: "Attributes",
kind: .collection(kind: "AttributeList", collectionElementName: "Attribute"),
nameForDiagnostics: "attributes",
description: "Attributes that are attached to the initializer.",
isOptional: true
),
Child(
name: "Modifiers",
kind: .collection(kind: "ModifierList", collectionElementName: "Modifier"),
nameForDiagnostics: "modifiers",
description: "Modifiers attached to the initializer",
isOptional: true
),
Child(
name: "InitKeyword",
kind: .token(choices: [.keyword(text: "init")])
kind: .token(choices: [.keyword(text: "init")]),
description: "The init keyword"
),
Child(
name: "OptionalMark",
kind: .token(choices: [.token(tokenKind: "PostfixQuestionMarkToken"), .token(tokenKind: "InfixQuestionMarkToken"), .token(tokenKind: "ExclamationMarkToken")]),
description: "If the initializer is failable, a question mark to indicate that.",
isOptional: true
),
Child(
name: "GenericParameterClause",
kind: .node(kind: "GenericParameterClause"),
nameForDiagnostics: "generic parameter clause",
description: "Generic parameters of the initializer.",
isOptional: true
),
Child(
name: "Signature",
kind: .node(kind: "FunctionSignature"),
nameForDiagnostics: "function signature"
nameForDiagnostics: "function signature",
description: "The arguments of the initializer. While the function signature allows specifying an return clause, doing so is not semantically valid."
),
Child(
name: "GenericWhereClause",
kind: .node(kind: "GenericWhereClause"),
nameForDiagnostics: "generic where clause",
description: "If the initializer had generic parameters, a where clause that can restrict those",
isOptional: true
),
Child(
name: "Body",
kind: .node(kind: "CodeBlock"),
description: "The initializer’s body. Missing if the initialier is a requirement of a protocol declaration.",
isOptional: true
),
]
Expand Down Expand Up @@ -1696,7 +1751,7 @@ public let DECL_NODES: [Node] = [
isOptional: true
),
Child(
name: "Members",
name: "MemberBlock",
kind: .node(kind: "MemberDeclBlock")
),
]
Expand Down Expand Up @@ -1798,7 +1853,7 @@ public let DECL_NODES: [Node] = [
isOptional: true
),
Child(
name: "Members",
name: "MemberBlock",
kind: .node(kind: "MemberDeclBlock")
),
]
Expand Down
4 changes: 2 additions & 2 deletions CodeGeneration/Sources/SyntaxSupport/KeywordSpec.swift
Original file line number Diff line number Diff line change
Expand Up @@ -96,7 +96,7 @@ public let KEYWORDS: [KeywordSpec] = [
KeywordSpec("autoclosure"),
KeywordSpec("availability"),
KeywordSpec("available"),
KeywordSpec("await"),
KeywordSpec("await", requiresTrailingSpace: true),
KeywordSpec("backDeployed"),
KeywordSpec("before"),
KeywordSpec("block"),
Expand All @@ -122,7 +122,7 @@ public let KEYWORDS: [KeywordSpec] = [
KeywordSpec("do", isLexerClassified: true),
KeywordSpec("dynamic"),
KeywordSpec("each"),
KeywordSpec("else", isLexerClassified: true, requiresTrailingSpace: true),
KeywordSpec("else", isLexerClassified: true, requiresLeadingSpace: true, requiresTrailingSpace: true),
KeywordSpec("enum", isLexerClassified: true, requiresTrailingSpace: true),
KeywordSpec("escaping"),
KeywordSpec("exclusivity"),
Expand Down
7 changes: 3 additions & 4 deletions CodeGeneration/Sources/SyntaxSupport/StmtNodes.swift
Original file line number Diff line number Diff line change
Expand Up @@ -290,18 +290,17 @@ public let STMT_NODES: [Node] = [
),
Child(
name: "TryKeyword",
kind: .node(kind: "TryToken"),
kind: .token(choices: [.keyword(text: "try")]),
isOptional: true
),
Child(
name: "AwaitKeyword",
kind: .token(choices: [.keyword(text: "await")]),
isOptional: true,
classification: "Keyword"
isOptional: true
),
Child(
name: "CaseKeyword",
kind: .node(kind: "CaseToken"),
kind: .token(choices: [.keyword(text: "case")]),
isOptional: true
),
Child(
Expand Down
2 changes: 1 addition & 1 deletion CodeGeneration/Sources/SyntaxSupport/Traits.swift
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ public let TRAITS: [Trait] = [
children: [
Child(name: "Attributes", kind: .node(kind: "AttributeList"), isOptional: true),
Child(name: "Modifiers", kind: .node(kind: "ModifierList"), isOptional: true),
Child(name: "Members", kind: .node(kind: "MemberDeclBlock")),
Child(name: "MemberBlock", kind: .node(kind: "MemberDeclBlock")),
]
),
Trait(
Expand Down
41 changes: 27 additions & 14 deletions CodeGeneration/Sources/Utils/SyntaxBuildableChild.swift
Original file line number Diff line number Diff line change
Expand Up @@ -45,21 +45,34 @@ public extension Child {
flattened(indentedDocumentation: description ?? "")
}

var defaultInitialization: ExprSyntax? {
switch kind {
case .token(choices: let choices, requiresLeadingSpace: _, requiresTrailingSpace: _):
if choices.count == 1, case .keyword(text: let text) = choices.first {
var textChoice = text
if textChoice == "init" {
textChoice = "`init`"
}
return ExprSyntax(".keyword(.\(raw: textChoice))")
} else {
return type.defaultInitialization
}
default:
return type.defaultInitialization
/// If the child node has a default value, return an expression of the form
/// ` = default_value` that can be used as the default value to for a
/// function parameter. Otherwise, return `nil`.
var defaultInitialization: InitializerClauseSyntax? {
if isOptional || isUnexpectedNodes {
return InitializerClauseSyntax(value: NilLiteralExprSyntax())
}
guard let token = token, isToken else {
return type.defaultValue.map { InitializerClauseSyntax(value: $0) }
}
if token.isKeyword {
return InitializerClauseSyntax(value: ExprSyntax(".\(raw: token.swiftKind)()"))
}
if token.text != nil {
return InitializerClauseSyntax(value: ExprSyntax(".\(raw: token.swiftKind)Token()"))
}
guard case .token(let choices, _, _) = kind, choices.count == 1, token.associatedValueClass != nil else {
return nil
}
var textChoice: String
switch choices[0] {
case .keyword(let text), .token(let text):
textChoice = text
}
if textChoice == "init" {
textChoice = "`init`"
}
return InitializerClauseSyntax(value: ExprSyntax(".\(raw: token.swiftKind)(.\(raw: textChoice))"))
}

/// If this node is a token that can't contain arbitrary text, generate a Swift
Expand Down
Loading