Skip to content

Commit 5e8636a

Browse files
committed
Implement recovery in eat
At the moment this doesn’t change anything because all places that call `eat` have previous checks that make sure the parser is currently positioned at the expected token. In the future, this will allow us to start parsing functions that `eat` a token at a different token and this function is responsible for eating all intermediate tokens until the expected one.
1 parent ac6f92b commit 5e8636a

15 files changed

+656
-275
lines changed

Sources/SwiftParser/Attributes.swift

Lines changed: 46 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -181,29 +181,33 @@ extension Parser {
181181
}
182182

183183

184-
let atSign = self.eat(.atSign)
184+
let (unexpectedBeforeAtSign, atSign) = self.eat(.atSign)
185185
let ident = self.consumeIdentifier()
186+
let unexpectedBeforeLeftParen: RawUnexpectedNodesSyntax?
186187
let leftParen: RawTokenSyntax?
187188
let arg: RawSyntax?
188189
let unexpectedBeforeRightParen: RawUnexpectedNodesSyntax?
189190
let rightParen: RawTokenSyntax?
190191
if self.at(.leftParen) {
191192
var args = [RawTokenSyntax]()
192-
leftParen = self.eat(.leftParen)
193+
(unexpectedBeforeLeftParen, leftParen) = self.eat(.leftParen)
193194
while !self.at(.eof), !self.at(.rightParen) {
194195
args.append(self.consumeAnyToken())
195196
}
196197
arg = RawSyntax(RawTokenListSyntax(elements: args, arena: self.arena))
197198
(unexpectedBeforeRightParen, rightParen) = self.expect(.rightParen)
198199
} else {
200+
unexpectedBeforeLeftParen = nil
199201
leftParen = nil
200202
arg = nil
201203
unexpectedBeforeRightParen = nil
202204
rightParen = nil
203205
}
204206
return RawSyntax(RawAttributeSyntax(
207+
unexpectedBeforeAtSign,
205208
atSignToken: atSign,
206209
attributeName: ident,
210+
unexpectedBeforeLeftParen,
207211
leftParen: leftParen,
208212
argument: arg,
209213
unexpectedBeforeRightParen,
@@ -213,7 +217,7 @@ extension Parser {
213217
}
214218

215219
mutating func parseCustomAttribute() -> RawCustomAttributeSyntax {
216-
let atSign = self.eat(.atSign)
220+
let (unexpectedBeforeAtSign, atSign) = self.eat(.atSign)
217221
let attrName = self.parseType()
218222

219223
// Custom attributes are stricter than normal attributes about their
@@ -224,11 +228,14 @@ extension Parser {
224228
leftParen: nil, argumentList: nil, rightParen: nil,
225229
arena: self.arena)
226230
}
227-
let leftParen = self.eat(.leftParen)
231+
let (unexpectedBeforeLeftParen, leftParen) = self.eat(.leftParen)
228232
let arguments = self.parseArgumentListElements()
229233
let (unexpectedBeforeRightParen, rightParen) = self.expect(.rightParen)
230234
return RawCustomAttributeSyntax(
231-
atSignToken: atSign, attributeName: attrName,
235+
unexpectedBeforeAtSign,
236+
atSignToken: atSign,
237+
attributeName: attrName,
238+
unexpectedBeforeLeftParen,
232239
leftParen: leftParen,
233240
argumentList: RawTupleExprElementListSyntax(elements: arguments, arena: self.arena),
234241
unexpectedBeforeRightParen,
@@ -239,7 +246,7 @@ extension Parser {
239246

240247
extension Parser {
241248
mutating func parseAvailabilityAttribute() -> RawAttributeSyntax {
242-
let atSign = self.eat(.atSign)
249+
let (unexpectedBeforeAtSign, atSign) = self.eat(.atSign)
243250
assert(self.currentToken.tokenText == "available")
244251
let available = self.consumeAnyToken()
245252
let (unexpectedBeforeLeftParen, leftParen) = self.expect(.leftParen)
@@ -257,6 +264,7 @@ extension Parser {
257264
let (unexpectedBeforeRightParen, rightParen) = self.expect(.rightParen)
258265

259266
return RawAttributeSyntax(
267+
unexpectedBeforeAtSign,
260268
atSignToken: atSign,
261269
attributeName: available,
262270
unexpectedBeforeLeftParen,
@@ -271,7 +279,7 @@ extension Parser {
271279

272280
extension Parser {
273281
mutating func parseDifferentiableAttribute() -> RawAttributeSyntax {
274-
let atSign = self.eat(.atSign)
282+
let (unexpectedBeforeAtSign, atSign) = self.eat(.atSign)
275283
assert(self.currentToken.tokenText == "differentiable")
276284
let differentiable = self.consumeAnyToken()
277285
let (unexpectedBeforeLeftParen, leftParen) = self.expect(.leftParen)
@@ -280,6 +288,7 @@ extension Parser {
280288
let (unexpectedBeforeRightParen, rightParen) = self.expect(.rightParen)
281289

282290
return RawAttributeSyntax(
291+
unexpectedBeforeAtSign,
283292
atSignToken: atSign,
284293
attributeName: differentiable,
285294
unexpectedBeforeLeftParen,
@@ -353,7 +362,7 @@ extension Parser {
353362
)
354363
}
355364

356-
let leftParen = self.eat(.leftParen)
365+
let (unexpectedBeforeLeftParen, leftParen) = self.eat(.leftParen)
357366
var elements = [RawDifferentiabilityParamSyntax]()
358367
while !self.at(.eof) && !self.at(.rightParen) {
359368
guard let param = self.parseDifferentiabilityParameter() else {
@@ -365,6 +374,7 @@ extension Parser {
365374

366375
let parameters = RawDifferentiabilityParamListSyntax(elements: elements, arena: self.arena)
367376
let list = RawDifferentiabilityParamsSyntax(
377+
unexpectedBeforeLeftParen,
368378
leftParen: leftParen,
369379
diffParams: parameters,
370380
unexpectedBeforeRightParen,
@@ -393,10 +403,14 @@ extension Parser {
393403
return RawDifferentiabilityParamSyntax(
394404
parameter: RawSyntax(token), trailingComma: comma, arena: self.arena)
395405
case .selfKeyword:
396-
let token = self.eat(.selfKeyword)
406+
let (unexpectedBeforeToken, token) = self.eat(.selfKeyword)
397407
let comma = self.consume(if: .comma)
398408
return RawDifferentiabilityParamSyntax(
399-
parameter: RawSyntax(token), trailingComma: comma, arena: self.arena)
409+
unexpectedBeforeToken,
410+
parameter: RawSyntax(token),
411+
trailingComma: comma,
412+
arena: self.arena
413+
)
400414
default:
401415
return nil
402416
}
@@ -405,27 +419,32 @@ extension Parser {
405419

406420
extension Parser {
407421
mutating func parseObjectiveCAttribute() -> RawAttributeSyntax {
408-
let atSign = self.eat(.atSign)
422+
let (unexpectedBeforeAtSign, atSign) = self.eat(.atSign)
409423
assert(self.currentToken.tokenText == "objc")
410424
let objc = self.consumeAnyToken()
411425

426+
let unexpectedBeforeLeftParen: RawUnexpectedNodesSyntax?
412427
let leftParen: RawTokenSyntax?
413428
let argument: RawObjCSelectorSyntax?
414429
let unexpectedBeforeRightParen: RawUnexpectedNodesSyntax?
415430
let rightParen: RawTokenSyntax?
416431
if self.at(.leftParen) {
417-
leftParen = self.eat(.leftParen)
432+
(unexpectedBeforeLeftParen, leftParen) = self.eat(.leftParen)
418433
argument = self.parseObjectiveCSelector()
419434
(unexpectedBeforeRightParen, rightParen) = self.expect(.rightParen)
420435
} else {
436+
unexpectedBeforeLeftParen = nil
421437
leftParen = nil
422438
argument = nil
423439
unexpectedBeforeRightParen = nil
424440
rightParen = nil
425441
}
426442

427443
return RawAttributeSyntax(
428-
atSignToken: atSign, attributeName: objc,
444+
unexpectedBeforeAtSign,
445+
atSignToken: atSign,
446+
attributeName: objc,
447+
unexpectedBeforeLeftParen,
429448
leftParen: leftParen,
430449
argument: argument.map(RawSyntax.init),
431450
unexpectedBeforeRightParen,
@@ -439,9 +458,13 @@ extension Parser {
439458
while !self.at(.eof) && !self.at(.rightParen) {
440459
// Empty selector piece.
441460
if self.at(.colon) {
442-
let colon = self.eat(.colon)
461+
let (unexpectedBeforeColon, colon) = self.eat(.colon)
443462
elements.append(RawObjCSelectorPieceSyntax(
444-
name: nil, colon: colon, arena: self.arena))
463+
name: nil,
464+
unexpectedBeforeColon,
465+
colon: colon,
466+
arena: self.arena
467+
))
445468
continue
446469
}
447470

@@ -461,13 +484,14 @@ extension Parser {
461484

462485
extension Parser {
463486
mutating func parseSpecializeAttribute() -> RawAttributeSyntax {
464-
let atSign = self.eat(.atSign)
487+
let (unexpectedBeforeAtSign, atSign) = self.eat(.atSign)
465488
assert(self.currentToken.tokenText == "_specialize")
466489
let specializeToken = self.consumeAnyToken()
467490
let (unexpectedBeforeLeftParen, leftParen) = self.expect(.leftParen)
468491
let argument = self.parseSpecializeAttributeSpecList()
469492
let (unexpectedBeforeRightParen, rightParen) = self.expect(.rightParen)
470493
return RawAttributeSyntax(
494+
unexpectedBeforeAtSign,
471495
atSignToken: atSign,
472496
attributeName: specializeToken,
473497
unexpectedBeforeLeftParen,
@@ -644,7 +668,7 @@ extension Parser {
644668

645669
extension Parser {
646670
mutating func parsePrivateImportAttribute() -> RawAttributeSyntax {
647-
let atSign = self.eat(.atSign)
671+
let (unexpectedBeforeAtSign, atSign) = self.eat(.atSign)
648672
assert(self.currentToken.tokenText == "_private")
649673
let privateToken = self.consumeAnyToken()
650674
let (unexpectedBeforeLeftParen, leftParen) = self.expect(.leftParen)
@@ -653,6 +677,7 @@ extension Parser {
653677
let filename = self.consumeAnyToken()
654678
let (unexpectedBeforeRightParen, rightParen) = self.expect(.rightParen)
655679
return RawAttributeSyntax(
680+
unexpectedBeforeAtSign,
656681
atSignToken: atSign,
657682
attributeName: privateToken,
658683
unexpectedBeforeLeftParen,
@@ -673,7 +698,7 @@ extension Parser {
673698

674699
extension Parser {
675700
mutating func parseDynamicReplacementAttribute() -> RawAttributeSyntax {
676-
let atSign = self.eat(.atSign)
701+
let (unexpectedBeforeAtSign, atSign) = self.eat(.atSign)
677702
assert(self.currentToken.tokenText == "_dynamicReplacement")
678703
let dynamicReplacementToken = self.consumeAnyToken()
679704
let (unexpectedBeforeLeftParen, leftParen) = self.expect(.leftParen)
@@ -690,6 +715,7 @@ extension Parser {
690715
let method = RawDeclNameSyntax(declBaseName: RawSyntax(base), declNameArguments: args, arena: self.arena)
691716
let (unexpectedBeforeRightParen, rightParen) = self.expect(.rightParen)
692717
return RawAttributeSyntax(
718+
unexpectedBeforeAtSign,
693719
atSignToken: atSign,
694720
attributeName: dynamicReplacementToken,
695721
unexpectedBeforeLeftParen,
@@ -710,13 +736,14 @@ extension Parser {
710736

711737
extension Parser {
712738
mutating func parseSPIAttribute() -> RawAttributeSyntax {
713-
let atSign = self.eat(.atSign)
739+
let (unexpectedBeforeAtSign, atSign) = self.eat(.atSign)
714740
assert(self.currentToken.tokenText == "_spi")
715741
let spiToken = self.consumeAnyToken()
716742
let (unexpectedBeforeLeftParen, leftParen) = self.expect(.leftParen)
717743
let label = self.consumeAnyToken()
718744
let (unexpectedBeforeRightParen, rightParen) = self.expect(.rightParen)
719745
return RawAttributeSyntax(
746+
unexpectedBeforeAtSign,
720747
atSignToken: atSign,
721748
attributeName: spiToken,
722749
unexpectedBeforeLeftParen,

Sources/SwiftParser/Availability.swift

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -129,10 +129,15 @@ extension Parser {
129129
case .deprecated:
130130
let argumentLabel = self.consumeAnyToken()
131131
if self.at(.colon) {
132-
let colon = self.eat(.colon)
132+
let (unexpectedBeforeColon, colon) = self.eat(.colon)
133133
let version = self.parseVersionTuple()
134134
entry = RawSyntax(RawAvailabilityLabeledArgumentSyntax(
135-
label: argumentLabel, colon: colon, value: RawSyntax(version), arena: self.arena))
135+
label: argumentLabel,
136+
unexpectedBeforeColon,
137+
colon: colon,
138+
value: RawSyntax(version),
139+
arena: self.arena
140+
))
136141
} else {
137142
entry = RawSyntax(argumentLabel)
138143
}

0 commit comments

Comments
 (0)