recover from missing semicolon

master
Vexu 2020-05-14 11:19:50 +03:00
parent ac319b2734
commit 89f2923a8a
No known key found for this signature in database
GPG Key ID: 59AEB8936E16A6AC
2 changed files with 30 additions and 3 deletions

View File

@ -667,7 +667,12 @@ fn parseStatement(arena: *Allocator, it: *TokenIterator, tree: *Tree) Error!?*No
if (try parseLabeledStatement(arena, it, tree)) |node| return node;
if (try parseSwitchExpr(arena, it, tree)) |node| return node;
if (try parseAssignExpr(arena, it, tree)) |node| {
_ = try expectToken(it, tree, .Semicolon);
_ = eatToken(it, .Semicolon) orelse {
try tree.errors.push(.{
.ExpectedToken = .{ .token = it.index, .expected_id = .Semicolon },
});
// pretend we saw a semicolon and continue parsing
};
return node;
}
@ -911,7 +916,12 @@ fn parseWhileStatement(arena: *Allocator, it: *TokenIterator, tree: *Tree) !?*No
fn parseBlockExprStatement(arena: *Allocator, it: *TokenIterator, tree: *Tree) !?*Node {
if (try parseBlockExpr(arena, it, tree)) |node| return node;
if (try parseAssignExpr(arena, it, tree)) |node| {
_ = try expectToken(it, tree, .Semicolon);
_ = eatToken(it, .Semicolon) orelse {
try tree.errors.push(.{
.ExpectedToken = .{ .token = it.index, .expected_id = .Semicolon },
});
// pretend we saw a semicolon and continue parsing
};
return node;
}
return null;
@ -3072,7 +3082,7 @@ fn parseDocComment(arena: *Allocator, it: *TokenIterator, tree: *Tree) !?*Node.D
}
/// Eat a single-line doc comment on the same line as another node
fn parseAppendedDocComment(arena: *Allocator, it: *TokenIterator, tree: *Tree, after_token: TokenIndex) Allocator.Error!?*Node.DocComment {
fn parseAppendedDocComment(arena: *Allocator, it: *TokenIterator, tree: *Tree, after_token: TokenIndex) !?*Node.DocComment {
const comment_token = eatToken(it, .DocComment) orelse return null;
if (tree.tokensOnSameLine(after_token, comment_token)) {
const node = try arena.create(Node.DocComment);

View File

@ -102,6 +102,23 @@ test "recovery: invalid extern/inline" {
});
}
test "recovery: missing semicolon" {
try testError(
\\test "" {
\\ comptime a && b
\\ c && d
\\ @foo
\\}
, &[_]Error{
.InvalidAnd,
.ExpectedToken,
.InvalidAnd,
.ExpectedToken,
.ExpectedParamList,
.ExpectedToken,
});
}
test "zig fmt: top-level fields" {
try testCanonical(
\\a: did_you_know,