Skip to content

Commit c0c5647

Browse files
committed
Add diagnostics for wrong modifiers for operator declarations & update test cases
1 parent 0a98797 commit c0c5647

File tree

2 files changed

+50
-1
lines changed

2 files changed

+50
-1
lines changed

Sources/SwiftParser/Declarations.swift

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1888,7 +1888,7 @@ extension Parser {
18881888
_ attrs: DeclAttributes,
18891889
_ handle: RecoveryConsumptionHandle
18901890
) -> RawOperatorDeclSyntax {
1891-
let (unexpectedBeforeOperatorKeyword, operatorKeyword) = self.eat(handle)
1891+
var (unexpectedBeforeOperatorKeyword, operatorKeyword) = self.eat(handle)
18921892
let unexpectedBeforeName: RawUnexpectedNodesSyntax?
18931893
let name: RawTokenSyntax
18941894
switch self.canRecoverTo(anyIn: OperatorLike.self) {
@@ -1965,14 +1965,29 @@ extension Parser {
19651965
unexpectedAtEnd = nil
19661966
}
19671967

1968+
var unexpectedBetweenAttributesAndModifiers: RawUnexpectedNodesSyntax?
19681969
var modifiers: RawModifierListSyntax? = attrs.modifiers
1970+
1971+
let expectedModifiers = [Keyword.prefix.defaultText, Keyword.postfix.defaultText, Keyword.infix.defaultText]
1972+
1973+
if let firstModifier = modifiers?.elements.first {
1974+
if !expectedModifiers.contains(firstModifier.name.tokenText) {
1975+
unexpectedBetweenAttributesAndModifiers = RawUnexpectedNodesSyntax([modifiers], arena: self.arena)
1976+
modifiers = nil
1977+
} else {
1978+
unexpectedBeforeOperatorKeyword = RawUnexpectedNodesSyntax([unexpectedBeforeOperatorKeyword, RawUnexpectedNodesSyntax(Array(modifiers!.elements.dropFirst()), arena: self.arena)], arena: self.arena)
1979+
modifiers = RawModifierListSyntax(elements: [firstModifier], arena: self.arena)
1980+
}
1981+
}
1982+
19691983
if modifiers == nil, unexpectedBeforeOperatorKeyword == nil {
19701984
let missedModifier = RawDeclModifierSyntax(name: self.missingToken(.prefix), detail: nil, arena: self.arena)
19711985
modifiers = RawModifierListSyntax(elements: [missedModifier], arena: self.arena)
19721986
}
19731987

19741988
return RawOperatorDeclSyntax(
19751989
attributes: attrs.attributes,
1990+
unexpectedBetweenAttributesAndModifiers,
19761991
modifiers: modifiers,
19771992
unexpectedBeforeOperatorKeyword,
19781993
operatorKeyword: operatorKeyword,

Tests/SwiftParserTest/translated/OperatorDeclTests.swift

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -480,6 +480,40 @@ final class OperatorDeclTests: XCTestCase {
480480
)
481481
}
482482

483+
func testOperatorDecl124() {
484+
assertParse(
485+
"""
486+
prefix 1️⃣mutating operator ?? : UndeclaredPrecedenceGroup
487+
""",
488+
diagnostics: [
489+
DiagnosticSpec(message: "unexpected code 'mutating' in operator declaration")
490+
]
491+
)
492+
}
493+
494+
func testOperatorDecl125() {
495+
assertParse(
496+
"""
497+
prefix 1️⃣postfix operator ** : PrecedenceGroup
498+
""",
499+
diagnostics: [
500+
DiagnosticSpec(message: "unexpected code 'postfix' in operator declaration")
501+
]
502+
)
503+
}
504+
505+
func testOperatorDecl126() {
506+
assertParse(
507+
"""
508+
1️⃣mutating 2️⃣operator ?? : PrecedenceGroup
509+
""",
510+
diagnostics: [
511+
DiagnosticSpec(message: "unexpected code 'mutating' before operator declaration"),
512+
DiagnosticSpec(locationMarker: "2️⃣", message: "operator must be declared as 'prefix', 'postfix', or 'infix'"),
513+
]
514+
)
515+
}
516+
483517
func testIdentifierAsOperatorName() {
484518
assertParse(
485519
"postfix operator 1️⃣aa",

0 commit comments

Comments
 (0)