authorgravatar for mail@isaacfreund.comIsaac Freund <mail@isaacfreund.com> 2021-02-19 22:54:47+01:00
committergravatar for mail@isaacfreund.comIsaac Freund <mail@isaacfreund.com> 2021-02-19 22:59:27+01:00
log95b95ea33e4b595d2fc6fbea850694b79f27fe55
tree7f22d836466700d51acaaf1a943dcdf8dd25f256
parent6f6568b1fdb30fc8574b3047470510b798307717
signaturelock-open Commit is signed but in an unrecognized format.

stage2: make same line doc comments a parse error

Allowing same line doc comments causes some ambiguity as to how generated docs should represent the case in which both same line and preceding line doc comments are present: /// preceding line const foobar = 42; /// same line Furthermore disallowing these makes things simpler as there is now only one way to add a doc comment to a decl or struct field.

3 files changed, 39 insertions(+), 59 deletions(-)

lib/std/zig/ast.zig+4
......@@ -146,6 +146,7 @@ pub const Tree = struct {
146146 .ExpectedFn => |*x| return x.render(tokens, stream),
147147 .ExpectedReturnType => |*x| return x.render(tokens, stream),
148148 .ExpectedAggregateKw => |*x| return x.render(tokens, stream),
149 .SameLineDocComment => |*x| return x.render(tokens, stream),
149150 .UnattachedDocComment => |*x| return x.render(tokens, stream),
150151 .ExpectedEqOrSemi => |*x| return x.render(tokens, stream),
151152 .ExpectedSemiOrLBrace => |*x| return x.render(tokens, stream),
......@@ -200,6 +201,7 @@ pub const Tree = struct {
200201 .ExpectedFn => |x| return x.token,
201202 .ExpectedReturnType => |x| return x.token,
202203 .ExpectedAggregateKw => |x| return x.token,
204 .SameLineDocComment => |x| return x.token,
203205 .UnattachedDocComment => |x| return x.token,
204206 .ExpectedEqOrSemi => |x| return x.token,
205207 .ExpectedSemiOrLBrace => |x| return x.token,
......@@ -2250,6 +2252,7 @@ pub const Error = union(enum) {
22502252 ExpectedFn: ExpectedFn,
22512253 ExpectedReturnType: ExpectedReturnType,
22522254 ExpectedAggregateKw: ExpectedAggregateKw,
2255 SameLineDocComment: SameLineDocComment,
22532256 UnattachedDocComment: UnattachedDocComment,
22542257 ExpectedEqOrSemi: ExpectedEqOrSemi,
22552258 ExpectedSemiOrLBrace: ExpectedSemiOrLBrace,
......@@ -2326,6 +2329,7 @@ pub const Error = union(enum) {
23262329
23272330 pub const ExpectedParamType = SimpleError("Expected parameter type");
23282331 pub const ExpectedPubItem = SimpleError("Expected function or variable declaration after pub");
2332 pub const SameLineDocComment = SimpleError("Same line documentation comment");
23292333 pub const UnattachedDocComment = SimpleError("Unattached documentation comment");
23302334 pub const ExtraAlignQualifier = SimpleError("Extra align qualifier");
23312335 pub const ExtraConstQualifier = SimpleError("Extra const qualifier");
lib/std/zig/parse.zig+10-16
......@@ -190,7 +190,7 @@ const Parser = struct {
190190
191191 var trailing_comma = false;
192192 while (true) {
193 const doc_comment = p.eatDocComments();
193 const doc_comment = try p.eatDocComments ();
194194
195195 switch (p.token_tags[p.tok_i]) {
196196 .keyword_test => {
......@@ -515,7 +515,6 @@ const Parser = struct {
515515 switch (p.token_tags[p.tok_i]) {
516516 .semicolon => {
517517 const semicolon_token = p.nextToken();
518 try p.parseAppendedDocComment(semicolon_token);
519518 return p.addNode(.{
520519 .tag = .fn_decl,
521520 .main_token = p.nodes.items(.main_token)[fn_proto],
......@@ -557,7 +556,6 @@ const Parser = struct {
557556 const var_decl = try p.parseVarDecl();
558557 if (var_decl != 0) {
559558 const semicolon_token = try p.expectToken(.semicolon);
560 try p.parseAppendedDocComment(semicolon_token);
561559 return var_decl;
562560 }
563561 if (thread_local_token != null) {
......@@ -585,7 +583,6 @@ const Parser = struct {
585583 const usingnamespace_token = try p.expectToken(.keyword_usingnamespace);
586584 const expr = try p.expectExpr();
587585 const semicolon_token = try p.expectToken(.semicolon);
588 try p.parseAppendedDocComment(semicolon_token);
589586 return p.addNode(.{
590587 .tag = .@"usingnamespace",
591588 .main_token = usingnamespace_token,
......@@ -2885,7 +2882,7 @@ const Parser = struct {
28852882 }
28862883
28872884 while (true) {
2888 const doc_comment = p.eatDocComments();
2885 const doc_comment = try p.eatDocComments();
28892886 const identifier = try p.expectToken(.identifier);
28902887 switch (p.token_tags[p.nextToken()]) {
28912888 .comma => {
......@@ -3274,7 +3271,7 @@ const Parser = struct {
32743271 /// such as in the case of anytype and `...`. Caller must look for rparen to find
32753272 /// out when there are no more param decls left.
32763273 fn expectParamDecl(p: *Parser) !Node.Index {
3277 _ = p.eatDocComments();
3274 _ = try p.eatDocComments();
32783275 switch (p.token_tags[p.tok_i]) {
32793276 .keyword_noalias, .keyword_comptime => p.tok_i += 1,
32803277 .ellipsis3 => {
......@@ -4075,8 +4072,13 @@ const Parser = struct {
40754072 }
40764073
40774074 /// Skips over doc comment tokens. Returns the first one, if any.
4078 fn eatDocComments(p: *Parser) ?TokenIndex {
4079 if (p.eatToken(.doc_comment)) |first_line| {
4075 fn eatDocComments(p: *Parser) !?TokenIndex {
4076 if (p.eatToken(.doc_comment)) |tok| {
4077 var first_line = tok;
4078 if (tok > 0 and tokensOnSameLine(p, tok - 1, tok)) {
4079 try p.warn(.{ .SameLineDocComment = .{ .token = tok } });
4080 first_line = p.eatToken(.doc_comment) orelse return null;
4081 }
40804082 while (p.eatToken(.doc_comment)) |_| {}
40814083 return first_line;
40824084 }
......@@ -4087,14 +4089,6 @@ const Parser = struct {
40874089 return std.mem.indexOfScalar(u8, p.source[p.token_starts[token1]..p.token_starts[token2]], '\n') == null;
40884090 }
40894091
4090 /// Eat a single-line doc comment on the same line as another node
4091 fn parseAppendedDocComment(p: *Parser, after_token: TokenIndex) !void {
4092 const comment_token = p.eatToken(.doc_comment) orelse return;
4093 if (!p.tokensOnSameLine(after_token, comment_token)) {
4094 p.tok_i -= 1;
4095 }
4096 }
4097
40984092 fn eatToken(p: *Parser, tag: Token.Tag) ?TokenIndex {
40994093 return if (p.token_tags[p.tok_i] == tag) p.nextToken() else null;
41004094 }
lib/std/zig/parser_test.zig+25-43
......@@ -1016,23 +1016,6 @@ test "zig fmt: linksection" {
10161016 );
10171017}
10181018
1019//test "zig fmt: correctly move doc comments on struct fields" {
1020// try testTransform(
1021// \\pub const section_64 = extern struct {
1022// \\ sectname: [16]u8, /// name of this section
1023// \\ segname: [16]u8, /// segment this section goes in
1024// \\};
1025// ,
1026// \\pub const section_64 = extern struct {
1027// \\ /// name of this section
1028// \\ sectname: [16]u8,
1029// \\ /// segment this section goes in
1030// \\ segname: [16]u8,
1031// \\};
1032// \\
1033// );
1034//}
1035
10361019test "zig fmt: correctly space struct fields with doc comments" {
10371020 try testTransform(
10381021 \\pub const S = struct {
......@@ -1449,31 +1432,6 @@ test "zig fmt: async call in if condition" {
14491432// \\
14501433// );
14511434//}
1452//
1453//test "zig fmt: same-line doc comment on variable declaration" {
1454// try testTransform(
1455// \\pub const MAP_ANONYMOUS = 0x1000; /// allocated from memory, swap space
1456// \\pub const MAP_FILE = 0x0000; /// map from file (default)
1457// \\
1458// \\pub const EMEDIUMTYPE = 124; /// Wrong medium type
1459// \\
1460// \\// nameserver query return codes
1461// \\pub const ENSROK = 0; /// DNS server returned answer with no data
1462// ,
1463// \\/// allocated from memory, swap space
1464// \\pub const MAP_ANONYMOUS = 0x1000;
1465// \\/// map from file (default)
1466// \\pub const MAP_FILE = 0x0000;
1467// \\
1468// \\/// Wrong medium type
1469// \\pub const EMEDIUMTYPE = 124;
1470// \\
1471// \\// nameserver query return codes
1472// \\/// DNS server returned answer with no data
1473// \\pub const ENSROK = 0;
1474// \\
1475// );
1476//}
14771435
14781436test "zig fmt: if-else with comment before else" {
14791437 try testCanonical(
......@@ -3625,6 +3583,30 @@ test "zig fmt: file ends with struct field" {
36253583// });
36263584//}
36273585
3586test "zig fmt: same line doc comment returns error" {
3587 try testError(
3588 \\const Foo = struct{
3589 \\ bar: u32, /// comment
3590 \\ foo: u32, /// comment
3591 \\ /// commment
3592 \\};
3593 \\
3594 \\const a = 42; /// comment
3595 \\
3596 \\extern fn foo() void; /// comment
3597 \\
3598 \\/// comment
3599 \\
3600 , &[_]Error{
3601 .SameLineDocComment,
3602 .SameLineDocComment,
3603 .UnattachedDocComment,
3604 .SameLineDocComment,
3605 .SameLineDocComment,
3606 .UnattachedDocComment,
3607 });
3608}
3609
36283610test "zig fmt: integer literals with underscore separators" {
36293611 try testTransform(
36303612 \\const
......@@ -4388,6 +4370,6 @@ fn testError(source: []const u8, expected_errors: []const Error) !void {
43884370
43894371 std.testing.expect(tree.errors.len == expected_errors.len);
43904372 for (expected_errors) |expected, i| {
4391 std.testing.expect(expected == tree.errors[i]);
4373 std.testing.expectEqual(expected, tree.errors[i]);
43924374 }
43934375}