| ... | ... | @@ -111,13 +111,13 @@ const Token = struct { |
| 111 | 111 | end: usize, |
| 112 | 112 | |
| 113 | 113 | const Id = enum { |
| 114 | | Invalid, |
| 115 | | Content, |
| 116 | | BracketOpen, |
| 117 | | TagContent, |
| 118 | | Separator, |
| 119 | | BracketClose, |
| 120 | | Eof, |
| 114 | invalid, |
| 115 | content, |
| 116 | bracket_open, |
| 117 | tag_content, |
| 118 | separator, |
| 119 | bracket_close, |
| 120 | eof, |
| 121 | 121 | }; |
| 122 | 122 | }; |
| 123 | 123 | |
| ... | ... | @@ -148,7 +148,7 @@ const Tokenizer = struct { |
| 148 | 148 | |
| 149 | 149 | fn next(self: *Tokenizer) Token { |
| 150 | 150 | var result = Token{ |
| 151 | | .id = Token.Id.Eof, |
| 151 | .id = .eof, |
| 152 | 152 | .start = self.index, |
| 153 | 153 | .end = undefined, |
| 154 | 154 | }; |
| ... | ... | @@ -160,33 +160,33 @@ const Tokenizer = struct { |
| 160 | 160 | self.state = State.LBracket; |
| 161 | 161 | }, |
| 162 | 162 | else => { |
| 163 | | result.id = Token.Id.Content; |
| 163 | result.id = .content; |
| 164 | 164 | }, |
| 165 | 165 | }, |
| 166 | 166 | State.LBracket => switch (c) { |
| 167 | 167 | '#' => { |
| 168 | | if (result.id != Token.Id.Eof) { |
| 168 | if (result.id != .eof) { |
| 169 | 169 | self.index -= 1; |
| 170 | 170 | self.state = State.Start; |
| 171 | 171 | break; |
| 172 | 172 | } else { |
| 173 | | result.id = Token.Id.BracketOpen; |
| 173 | result.id = .bracket_open; |
| 174 | 174 | self.index += 1; |
| 175 | 175 | self.state = State.TagName; |
| 176 | 176 | break; |
| 177 | 177 | } |
| 178 | 178 | }, |
| 179 | 179 | else => { |
| 180 | | result.id = Token.Id.Content; |
| 180 | result.id = .content; |
| 181 | 181 | self.state = State.Start; |
| 182 | 182 | }, |
| 183 | 183 | }, |
| 184 | 184 | State.TagName => switch (c) { |
| 185 | 185 | '|' => { |
| 186 | | if (result.id != Token.Id.Eof) { |
| 186 | if (result.id != .eof) { |
| 187 | 187 | break; |
| 188 | 188 | } else { |
| 189 | | result.id = Token.Id.Separator; |
| 189 | result.id = .separator; |
| 190 | 190 | self.index += 1; |
| 191 | 191 | break; |
| 192 | 192 | } |
| ... | ... | @@ -195,24 +195,24 @@ const Tokenizer = struct { |
| 195 | 195 | self.state = State.Hash; |
| 196 | 196 | }, |
| 197 | 197 | else => { |
| 198 | | result.id = Token.Id.TagContent; |
| 198 | result.id = .tag_content; |
| 199 | 199 | }, |
| 200 | 200 | }, |
| 201 | 201 | State.Hash => switch (c) { |
| 202 | 202 | '}' => { |
| 203 | | if (result.id != Token.Id.Eof) { |
| 203 | if (result.id != .eof) { |
| 204 | 204 | self.index -= 1; |
| 205 | 205 | self.state = State.TagName; |
| 206 | 206 | break; |
| 207 | 207 | } else { |
| 208 | | result.id = Token.Id.BracketClose; |
| 208 | result.id = .bracket_close; |
| 209 | 209 | self.index += 1; |
| 210 | 210 | self.state = State.Start; |
| 211 | 211 | break; |
| 212 | 212 | } |
| 213 | 213 | }, |
| 214 | 214 | else => { |
| 215 | | result.id = Token.Id.TagContent; |
| 215 | result.id = .tag_content; |
| 216 | 216 | self.state = State.TagName; |
| 217 | 217 | }, |
| 218 | 218 | }, |
| ... | ... | @@ -222,7 +222,7 @@ const Tokenizer = struct { |
| 222 | 222 | switch (self.state) { |
| 223 | 223 | State.Start, State.LBracket, State.Eof => {}, |
| 224 | 224 | else => { |
| 225 | | result.id = Token.Id.Invalid; |
| 225 | result.id = .invalid; |
| 226 | 226 | }, |
| 227 | 227 | } |
| 228 | 228 | self.state = State.Eof; |
| ... | ... | @@ -404,38 +404,38 @@ fn genToc(allocator: Allocator, tokenizer: *Tokenizer) !Toc { |
| 404 | 404 | while (true) { |
| 405 | 405 | const token = tokenizer.next(); |
| 406 | 406 | switch (token.id) { |
| 407 | | Token.Id.Eof => { |
| 407 | .eof => { |
| 408 | 408 | if (header_stack_size != 0) { |
| 409 | 409 | return parseError(tokenizer, token, "unbalanced headers", .{}); |
| 410 | 410 | } |
| 411 | 411 | try toc.writeAll(" </ul>\n"); |
| 412 | 412 | break; |
| 413 | 413 | }, |
| 414 | | Token.Id.Content => { |
| 414 | .content => { |
| 415 | 415 | try nodes.append(Node{ .Content = tokenizer.buffer[token.start..token.end] }); |
| 416 | 416 | }, |
| 417 | | Token.Id.BracketOpen => { |
| 418 | | const tag_token = try eatToken(tokenizer, Token.Id.TagContent); |
| 417 | .bracket_open => { |
| 418 | const tag_token = try eatToken(tokenizer, .tag_content); |
| 419 | 419 | const tag_name = tokenizer.buffer[tag_token.start..tag_token.end]; |
| 420 | 420 | |
| 421 | 421 | if (mem.eql(u8, tag_name, "nav")) { |
| 422 | | _ = try eatToken(tokenizer, Token.Id.BracketClose); |
| 422 | _ = try eatToken(tokenizer, .bracket_close); |
| 423 | 423 | |
| 424 | 424 | try nodes.append(Node.Nav); |
| 425 | 425 | } else if (mem.eql(u8, tag_name, "builtin")) { |
| 426 | | _ = try eatToken(tokenizer, Token.Id.BracketClose); |
| 426 | _ = try eatToken(tokenizer, .bracket_close); |
| 427 | 427 | try nodes.append(Node{ .Builtin = tag_token }); |
| 428 | 428 | } else if (mem.eql(u8, tag_name, "header_open")) { |
| 429 | | _ = try eatToken(tokenizer, Token.Id.Separator); |
| 430 | | const content_token = try eatToken(tokenizer, Token.Id.TagContent); |
| 429 | _ = try eatToken(tokenizer, .separator); |
| 430 | const content_token = try eatToken(tokenizer, .tag_content); |
| 431 | 431 | const content = tokenizer.buffer[content_token.start..content_token.end]; |
| 432 | 432 | var columns: ?u8 = null; |
| 433 | 433 | while (true) { |
| 434 | 434 | const bracket_tok = tokenizer.next(); |
| 435 | 435 | switch (bracket_tok.id) { |
| 436 | | .BracketClose => break, |
| 437 | | .Separator => continue, |
| 438 | | .TagContent => { |
| 436 | .bracket_close => break, |
| 437 | .separator => continue, |
| 438 | .tag_content => { |
| 439 | 439 | const param = tokenizer.buffer[bracket_tok.start..bracket_tok.end]; |
| 440 | 440 | if (mem.eql(u8, param, "2col")) { |
| 441 | 441 | columns = 2; |
| ... | ... | @@ -486,7 +486,7 @@ fn genToc(allocator: Allocator, tokenizer: *Tokenizer) !Toc { |
| 486 | 486 | return parseError(tokenizer, tag_token, "unbalanced close header", .{}); |
| 487 | 487 | } |
| 488 | 488 | header_stack_size -= 1; |
| 489 | | _ = try eatToken(tokenizer, Token.Id.BracketClose); |
| 489 | _ = try eatToken(tokenizer, .bracket_close); |
| 490 | 490 | |
| 491 | 491 | if (last_action == Action.Close) { |
| 492 | 492 | try toc.writeByteNTimes(' ', 8 + header_stack_size * 4); |
| ... | ... | @@ -502,15 +502,15 @@ fn genToc(allocator: Allocator, tokenizer: *Tokenizer) !Toc { |
| 502 | 502 | while (true) { |
| 503 | 503 | const see_also_tok = tokenizer.next(); |
| 504 | 504 | switch (see_also_tok.id) { |
| 505 | | Token.Id.TagContent => { |
| 505 | .tag_content => { |
| 506 | 506 | const content = tokenizer.buffer[see_also_tok.start..see_also_tok.end]; |
| 507 | 507 | try list.append(SeeAlsoItem{ |
| 508 | 508 | .name = content, |
| 509 | 509 | .token = see_also_tok, |
| 510 | 510 | }); |
| 511 | 511 | }, |
| 512 | | Token.Id.Separator => {}, |
| 513 | | Token.Id.BracketClose => { |
| 512 | .separator => {}, |
| 513 | .bracket_close => { |
| 514 | 514 | try nodes.append(Node{ .SeeAlso = try list.toOwnedSlice() }); |
| 515 | 515 | break; |
| 516 | 516 | }, |
| ... | ... | @@ -518,17 +518,17 @@ fn genToc(allocator: Allocator, tokenizer: *Tokenizer) !Toc { |
| 518 | 518 | } |
| 519 | 519 | } |
| 520 | 520 | } else if (mem.eql(u8, tag_name, "link")) { |
| 521 | | _ = try eatToken(tokenizer, Token.Id.Separator); |
| 522 | | const name_tok = try eatToken(tokenizer, Token.Id.TagContent); |
| 521 | _ = try eatToken(tokenizer, .separator); |
| 522 | const name_tok = try eatToken(tokenizer, .tag_content); |
| 523 | 523 | const name = tokenizer.buffer[name_tok.start..name_tok.end]; |
| 524 | 524 | |
| 525 | 525 | const url_name = blk: { |
| 526 | 526 | const tok = tokenizer.next(); |
| 527 | 527 | switch (tok.id) { |
| 528 | | Token.Id.BracketClose => break :blk name, |
| 529 | | Token.Id.Separator => { |
| 530 | | const explicit_text = try eatToken(tokenizer, Token.Id.TagContent); |
| 531 | | _ = try eatToken(tokenizer, Token.Id.BracketClose); |
| 528 | .bracket_close => break :blk name, |
| 529 | .separator => { |
| 530 | const explicit_text = try eatToken(tokenizer, .tag_content); |
| 531 | _ = try eatToken(tokenizer, .bracket_close); |
| 532 | 532 | break :blk tokenizer.buffer[explicit_text.start..explicit_text.end]; |
| 533 | 533 | }, |
| 534 | 534 | else => return parseError(tokenizer, tok, "invalid link token", .{}), |
| ... | ... | @@ -543,20 +543,20 @@ fn genToc(allocator: Allocator, tokenizer: *Tokenizer) !Toc { |
| 543 | 543 | }, |
| 544 | 544 | }); |
| 545 | 545 | } else if (mem.eql(u8, tag_name, "code_begin")) { |
| 546 | | _ = try eatToken(tokenizer, Token.Id.Separator); |
| 547 | | const code_kind_tok = try eatToken(tokenizer, Token.Id.TagContent); |
| 548 | | _ = try eatToken(tokenizer, Token.Id.Separator); |
| 549 | | const name_tok = try eatToken(tokenizer, Token.Id.TagContent); |
| 546 | _ = try eatToken(tokenizer, .separator); |
| 547 | const code_kind_tok = try eatToken(tokenizer, .tag_content); |
| 548 | _ = try eatToken(tokenizer, .separator); |
| 549 | const name_tok = try eatToken(tokenizer, .tag_content); |
| 550 | 550 | const name = tokenizer.buffer[name_tok.start..name_tok.end]; |
| 551 | 551 | var error_str: []const u8 = ""; |
| 552 | 552 | const maybe_sep = tokenizer.next(); |
| 553 | 553 | switch (maybe_sep.id) { |
| 554 | | Token.Id.Separator => { |
| 555 | | const error_tok = try eatToken(tokenizer, Token.Id.TagContent); |
| 554 | .separator => { |
| 555 | const error_tok = try eatToken(tokenizer, .tag_content); |
| 556 | 556 | error_str = tokenizer.buffer[error_tok.start..error_tok.end]; |
| 557 | | _ = try eatToken(tokenizer, Token.Id.BracketClose); |
| 557 | _ = try eatToken(tokenizer, .bracket_close); |
| 558 | 558 | }, |
| 559 | | Token.Id.BracketClose => {}, |
| 559 | .bracket_close => {}, |
| 560 | 560 | else => return parseError(tokenizer, token, "invalid token", .{}), |
| 561 | 561 | } |
| 562 | 562 | const code_kind_str = tokenizer.buffer[code_kind_tok.start..code_kind_tok.end]; |
| ... | ... | @@ -599,9 +599,9 @@ fn genToc(allocator: Allocator, tokenizer: *Tokenizer) !Toc { |
| 599 | 599 | defer additional_options.deinit(); |
| 600 | 600 | |
| 601 | 601 | const source_token = while (true) { |
| 602 | | const content_tok = try eatToken(tokenizer, Token.Id.Content); |
| 603 | | _ = try eatToken(tokenizer, Token.Id.BracketOpen); |
| 604 | | const end_code_tag = try eatToken(tokenizer, Token.Id.TagContent); |
| 602 | const content_tok = try eatToken(tokenizer, .content); |
| 603 | _ = try eatToken(tokenizer, .bracket_open); |
| 604 | const end_code_tag = try eatToken(tokenizer, .tag_content); |
| 605 | 605 | const end_tag_name = tokenizer.buffer[end_code_tag.start..end_code_tag.end]; |
| 606 | 606 | if (mem.eql(u8, end_tag_name, "code_release_fast")) { |
| 607 | 607 | mode = .ReleaseFast; |
| ... | ... | @@ -612,8 +612,8 @@ fn genToc(allocator: Allocator, tokenizer: *Tokenizer) !Toc { |
| 612 | 612 | } else if (mem.eql(u8, end_tag_name, "code_verbose_cimport")) { |
| 613 | 613 | verbose_cimport = true; |
| 614 | 614 | } else if (mem.eql(u8, end_tag_name, "code_link_object")) { |
| 615 | | _ = try eatToken(tokenizer, Token.Id.Separator); |
| 616 | | const obj_tok = try eatToken(tokenizer, Token.Id.TagContent); |
| 615 | _ = try eatToken(tokenizer, .separator); |
| 616 | const obj_tok = try eatToken(tokenizer, .tag_content); |
| 617 | 617 | try link_objects.append(tokenizer.buffer[obj_tok.start..obj_tok.end]); |
| 618 | 618 | } else if (mem.eql(u8, end_tag_name, "target_windows")) { |
| 619 | 619 | target_str = "x86_64-windows"; |
| ... | ... | @@ -630,11 +630,11 @@ fn genToc(allocator: Allocator, tokenizer: *Tokenizer) !Toc { |
| 630 | 630 | } else if (mem.eql(u8, end_tag_name, "link_mode_dynamic")) { |
| 631 | 631 | link_mode = .Dynamic; |
| 632 | 632 | } else if (mem.eql(u8, end_tag_name, "additonal_option")) { |
| 633 | | _ = try eatToken(tokenizer, Token.Id.Separator); |
| 634 | | const option = try eatToken(tokenizer, Token.Id.TagContent); |
| 633 | _ = try eatToken(tokenizer, .separator); |
| 634 | const option = try eatToken(tokenizer, .tag_content); |
| 635 | 635 | try additional_options.append(tokenizer.buffer[option.start..option.end]); |
| 636 | 636 | } else if (mem.eql(u8, end_tag_name, "code_end")) { |
| 637 | | _ = try eatToken(tokenizer, Token.Id.BracketClose); |
| 637 | _ = try eatToken(tokenizer, .bracket_close); |
| 638 | 638 | break content_tok; |
| 639 | 639 | } else { |
| 640 | 640 | return parseError( |
| ... | ... | @@ -644,7 +644,7 @@ fn genToc(allocator: Allocator, tokenizer: *Tokenizer) !Toc { |
| 644 | 644 | .{end_tag_name}, |
| 645 | 645 | ); |
| 646 | 646 | } |
| 647 | | _ = try eatToken(tokenizer, Token.Id.BracketClose); |
| 647 | _ = try eatToken(tokenizer, .bracket_close); |
| 648 | 648 | } else unreachable; // TODO issue #707 |
| 649 | 649 | try nodes.append(Node{ |
| 650 | 650 | .Code = Code{ |
| ... | ... | @@ -664,10 +664,10 @@ fn genToc(allocator: Allocator, tokenizer: *Tokenizer) !Toc { |
| 664 | 664 | }); |
| 665 | 665 | tokenizer.code_node_count += 1; |
| 666 | 666 | } else if (mem.eql(u8, tag_name, "syntax")) { |
| 667 | | _ = try eatToken(tokenizer, Token.Id.BracketClose); |
| 668 | | const content_tok = try eatToken(tokenizer, Token.Id.Content); |
| 669 | | _ = try eatToken(tokenizer, Token.Id.BracketOpen); |
| 670 | | const end_syntax_tag = try eatToken(tokenizer, Token.Id.TagContent); |
| 667 | _ = try eatToken(tokenizer, .bracket_close); |
| 668 | const content_tok = try eatToken(tokenizer, .content); |
| 669 | _ = try eatToken(tokenizer, .bracket_open); |
| 670 | const end_syntax_tag = try eatToken(tokenizer, .tag_content); |
| 671 | 671 | const end_tag_name = tokenizer.buffer[end_syntax_tag.start..end_syntax_tag.end]; |
| 672 | 672 | if (!mem.eql(u8, end_tag_name, "endsyntax")) { |
| 673 | 673 | return parseError( |
| ... | ... | @@ -677,13 +677,13 @@ fn genToc(allocator: Allocator, tokenizer: *Tokenizer) !Toc { |
| 677 | 677 | .{end_tag_name}, |
| 678 | 678 | ); |
| 679 | 679 | } |
| 680 | | _ = try eatToken(tokenizer, Token.Id.BracketClose); |
| 680 | _ = try eatToken(tokenizer, .bracket_close); |
| 681 | 681 | try nodes.append(Node{ .InlineSyntax = content_tok }); |
| 682 | 682 | } else if (mem.eql(u8, tag_name, "shell_samp")) { |
| 683 | | _ = try eatToken(tokenizer, Token.Id.BracketClose); |
| 684 | | const content_tok = try eatToken(tokenizer, Token.Id.Content); |
| 685 | | _ = try eatToken(tokenizer, Token.Id.BracketOpen); |
| 686 | | const end_syntax_tag = try eatToken(tokenizer, Token.Id.TagContent); |
| 683 | _ = try eatToken(tokenizer, .bracket_close); |
| 684 | const content_tok = try eatToken(tokenizer, .content); |
| 685 | _ = try eatToken(tokenizer, .bracket_open); |
| 686 | const end_syntax_tag = try eatToken(tokenizer, .tag_content); |
| 687 | 687 | const end_tag_name = tokenizer.buffer[end_syntax_tag.start..end_syntax_tag.end]; |
| 688 | 688 | if (!mem.eql(u8, end_tag_name, "end_shell_samp")) { |
| 689 | 689 | return parseError( |
| ... | ... | @@ -693,20 +693,20 @@ fn genToc(allocator: Allocator, tokenizer: *Tokenizer) !Toc { |
| 693 | 693 | .{end_tag_name}, |
| 694 | 694 | ); |
| 695 | 695 | } |
| 696 | | _ = try eatToken(tokenizer, Token.Id.BracketClose); |
| 696 | _ = try eatToken(tokenizer, .bracket_close); |
| 697 | 697 | try nodes.append(Node{ .Shell = content_tok }); |
| 698 | 698 | } else if (mem.eql(u8, tag_name, "syntax_block")) { |
| 699 | | _ = try eatToken(tokenizer, Token.Id.Separator); |
| 700 | | const source_type_tok = try eatToken(tokenizer, Token.Id.TagContent); |
| 699 | _ = try eatToken(tokenizer, .separator); |
| 700 | const source_type_tok = try eatToken(tokenizer, .tag_content); |
| 701 | 701 | var name: []const u8 = "sample_code"; |
| 702 | 702 | const maybe_sep = tokenizer.next(); |
| 703 | 703 | switch (maybe_sep.id) { |
| 704 | | Token.Id.Separator => { |
| 705 | | const name_tok = try eatToken(tokenizer, Token.Id.TagContent); |
| 704 | .separator => { |
| 705 | const name_tok = try eatToken(tokenizer, .tag_content); |
| 706 | 706 | name = tokenizer.buffer[name_tok.start..name_tok.end]; |
| 707 | | _ = try eatToken(tokenizer, Token.Id.BracketClose); |
| 707 | _ = try eatToken(tokenizer, .bracket_close); |
| 708 | 708 | }, |
| 709 | | Token.Id.BracketClose => {}, |
| 709 | .bracket_close => {}, |
| 710 | 710 | else => return parseError(tokenizer, token, "invalid token", .{}), |
| 711 | 711 | } |
| 712 | 712 | const source_type_str = tokenizer.buffer[source_type_tok.start..source_type_tok.end]; |
| ... | ... | @@ -723,12 +723,12 @@ fn genToc(allocator: Allocator, tokenizer: *Tokenizer) !Toc { |
| 723 | 723 | return parseError(tokenizer, source_type_tok, "unrecognized code kind: {s}", .{source_type_str}); |
| 724 | 724 | } |
| 725 | 725 | const source_token = while (true) { |
| 726 | | const content_tok = try eatToken(tokenizer, Token.Id.Content); |
| 727 | | _ = try eatToken(tokenizer, Token.Id.BracketOpen); |
| 728 | | const end_code_tag = try eatToken(tokenizer, Token.Id.TagContent); |
| 726 | const content_tok = try eatToken(tokenizer, .content); |
| 727 | _ = try eatToken(tokenizer, .bracket_open); |
| 728 | const end_code_tag = try eatToken(tokenizer, .tag_content); |
| 729 | 729 | const end_tag_name = tokenizer.buffer[end_code_tag.start..end_code_tag.end]; |
| 730 | 730 | if (mem.eql(u8, end_tag_name, "end_syntax_block")) { |
| 731 | | _ = try eatToken(tokenizer, Token.Id.BracketClose); |
| 731 | _ = try eatToken(tokenizer, .bracket_close); |
| 732 | 732 | break content_tok; |
| 733 | 733 | } else { |
| 734 | 734 | return parseError( |
| ... | ... | @@ -738,7 +738,7 @@ fn genToc(allocator: Allocator, tokenizer: *Tokenizer) !Toc { |
| 738 | 738 | .{end_tag_name}, |
| 739 | 739 | ); |
| 740 | 740 | } |
| 741 | | _ = try eatToken(tokenizer, Token.Id.BracketClose); |
| 741 | _ = try eatToken(tokenizer, .bracket_close); |
| 742 | 742 | }; |
| 743 | 743 | try nodes.append(Node{ .SyntaxBlock = SyntaxBlock{ .source_type = source_type, .name = name, .source_token = source_token } }); |
| 744 | 744 | } else { |