| author | |
| committer | |
| log | 37d3ef28351027a83249080d3238d61d9346f6db |
| tree | 6bad32bd19b6655960ca706c862989bc6aee9fec |
| parent | 47680cc0d806775dd9576faaff6303e88b14fb5a |
4 files changed, 68 insertions(+), 2 deletions(-)
std/zig/ast.zig+32| ... | ... | @@ -36,6 +36,7 @@ pub const Node = struct { |
| 36 | 36 | VarType, |
| 37 | 37 | ErrorType, |
| 38 | 38 | FnProto, |
| 39 | PromiseType, | |
| 39 | 40 | |
| 40 | 41 | // Primary expressions |
| 41 | 42 | IntegerLiteral, |
| ... | ... | @@ -495,6 +496,37 @@ pub const Node = struct { |
| 495 | 496 | } |
| 496 | 497 | }; |
| 497 | 498 | |
| 499 | pub const PromiseType = struct { | |
| 500 | base: Node, | |
| 501 | promise_token: Token, | |
| 502 | result: ?Result, | |
| 503 | ||
| 504 | pub const Result = struct { | |
| 505 | arrow_token: Token, | |
| 506 | return_type: &Node, | |
| 507 | }; | |
| 508 | ||
| 509 | pub fn iterate(self: &PromiseType, index: usize) ?&Node { | |
| 510 | var i = index; | |
| 511 | ||
| 512 | if (self.result) |result| { | |
| 513 | if (i < 1) return result.return_type; | |
| 514 | i -= 1; | |
| 515 | } | |
| 516 | ||
| 517 | return null; | |
| 518 | } | |
| 519 | ||
| 520 | pub fn firstToken(self: &PromiseType) Token { | |
| 521 | return self.promise_token; | |
| 522 | } | |
| 523 | ||
| 524 | pub fn lastToken(self: &PromiseType) Token { | |
| 525 | if (self.result) |result| return result.return_type.lastToken(); | |
| 526 | return self.promise_token; | |
| 527 | } | |
| 528 | }; | |
| 529 | ||
| 498 | 530 | pub const ParamDecl = struct { |
| 499 | 531 | base: Node, |
| 500 | 532 | comptime_token: ?Token, |
std/zig/parser.zig+32| ... | ... | @@ -2550,6 +2550,30 @@ pub const Parser = struct { |
| 2550 | 2550 | _ = try self.createToCtxLiteral(arena, opt_ctx, ast.Node.Unreachable, token); |
| 2551 | 2551 | continue; |
| 2552 | 2552 | }, |
| 2553 | Token.Id.Keyword_promise => { | |
| 2554 | const node = try arena.construct(ast.Node.PromiseType { | |
| 2555 | .base = ast.Node { | |
| 2556 | .id = ast.Node.Id.PromiseType, | |
| 2557 | .doc_comments = null, | |
| 2558 | .same_line_comment = null, | |
| 2559 | }, | |
| 2560 | .promise_token = token, | |
| 2561 | .result = null, | |
| 2562 | }); | |
| 2563 | opt_ctx.store(&node.base); | |
| 2564 | const next_token = self.getNextToken(); | |
| 2565 | if (next_token.id != Token.Id.Arrow) { | |
| 2566 | self.putBackToken(next_token); | |
| 2567 | continue; | |
| 2568 | } | |
| 2569 | node.result = ast.Node.PromiseType.Result { | |
| 2570 | .arrow_token = next_token, | |
| 2571 | .return_type = undefined, | |
| 2572 | }; | |
| 2573 | const return_type_ptr = &((??node.result).return_type); | |
| 2574 | try stack.append(State { .Expression = OptionalCtx { .Required = return_type_ptr, } }); | |
| 2575 | continue; | |
| 2576 | }, | |
| 2553 | 2577 | Token.Id.StringLiteral, Token.Id.MultilineStringLiteralLine => { |
| 2554 | 2578 | opt_ctx.store((try self.parseStringLiteral(arena, token)) ?? unreachable); |
| 2555 | 2579 | continue; |
| ... | ... | @@ -4147,6 +4171,14 @@ pub const Parser = struct { |
| 4147 | 4171 | try stack.append(RenderState { .Text = self.tokenizer.getTokenSlice(visib_token) }); |
| 4148 | 4172 | } |
| 4149 | 4173 | }, |
| 4174 | ast.Node.Id.PromiseType => { | |
| 4175 | const promise_type = @fieldParentPtr(ast.Node.PromiseType, "base", base); | |
| 4176 | try stream.write(self.tokenizer.getTokenSlice(promise_type.promise_token)); | |
| 4177 | if (promise_type.result) |result| { | |
| 4178 | try stream.write(self.tokenizer.getTokenSlice(result.arrow_token)); | |
| 4179 | try stack.append(RenderState { .Expression = result.return_type}); | |
| 4180 | } | |
| 4181 | }, | |
| 4150 | 4182 | ast.Node.Id.LineComment => { |
| 4151 | 4183 | const line_comment_node = @fieldParentPtr(ast.Node.LineComment, "base", base); |
| 4152 | 4184 | try stream.write(self.tokenizer.getTokenSlice(line_comment_node.token)); |
std/zig/parser_test.zig+2-2| ... | ... | @@ -948,12 +948,12 @@ test "zig fmt: coroutines" { |
| 948 | 948 | \\ suspend; |
| 949 | 949 | \\ x += 1; |
| 950 | 950 | \\ suspend |p| {} |
| 951 | \\ const p = async simpleAsyncFn() catch unreachable; | |
| 951 | \\ const p: promise->void = async simpleAsyncFn() catch unreachable; | |
| 952 | 952 | \\ await p; |
| 953 | 953 | \\} |
| 954 | 954 | \\ |
| 955 | 955 | \\test "coroutine suspend, resume, cancel" { |
| 956 | \\ const p = try async<std.debug.global_allocator> testAsyncSeq(); | |
| 956 | \\ const p: promise = try async<std.debug.global_allocator> testAsyncSeq(); | |
| 957 | 957 | \\ resume p; |
| 958 | 958 | \\ cancel p; |
| 959 | 959 | \\} |
std/zig/tokenizer.zig+2| ... | ... | @@ -40,6 +40,7 @@ pub const Token = struct { |
| 40 | 40 | KeywordId{.bytes="null", .id = Id.Keyword_null}, |
| 41 | 41 | KeywordId{.bytes="or", .id = Id.Keyword_or}, |
| 42 | 42 | KeywordId{.bytes="packed", .id = Id.Keyword_packed}, |
| 43 | KeywordId{.bytes="promise", .id = Id.Keyword_promise}, | |
| 43 | 44 | KeywordId{.bytes="pub", .id = Id.Keyword_pub}, |
| 44 | 45 | KeywordId{.bytes="resume", .id = Id.Keyword_resume}, |
| 45 | 46 | KeywordId{.bytes="return", .id = Id.Keyword_return}, |
| ... | ... | @@ -166,6 +167,7 @@ pub const Token = struct { |
| 166 | 167 | Keyword_null, |
| 167 | 168 | Keyword_or, |
| 168 | 169 | Keyword_packed, |
| 170 | Keyword_promise, | |
| 169 | 171 | Keyword_pub, |
| 170 | 172 | Keyword_resume, |
| 171 | 173 | Keyword_return, |