From 11deb14dc65625ac72296a69ee262051e53c43e0 Mon Sep 17 00:00:00 2001 From: Jon Ross-Perkins Date: Wed, 28 Dec 2022 12:55:40 -0800 Subject: [PATCH] Handle `var` init-with-self situations. (#2488) The problem I'm trying to solve is: `var x: i32 = x;`. This change makes it so that name lookup fails, by removing `x` from name lookup between the `=` and `;`. `var x: i32` still adds to name lookup to handle future situations like `var (x: i32, x: i32);` which is still a redefinition of `x`; if we don't add `x` to name lookup, it gets harder to catch that example. The VariableDeclaration/VariableInitializer refactor in ParseTree supports this by given a bracketing-like structure for semantics to cue that it's entering an initialization expression. With this, VariableInitializer can remove the name lookup and queue it to be restored. VariableDeclaration doesn't need to change too much since it's still bracketed by VariableIntroducer, and so we just traverse slightly differently. Note this also incidentally changes a little about NameReference, that it's returning the storage consistently instead of the name. You can see this e.g. in global_lookup.carbon, `Assign(node8, node4): node2;` using node4 (VarStorage) instead of Node5 (BindName). Really either _could_ work, since from a BindName we can get to the VarStorage, and that may be reason to switch later if we find it preferable to have the BindName for whatever reason. But the *actual* value in NameLookup is a BindName so that errors can associate with the _name_ instead of the "storage" parse node, which is currently the `:`. This is mainly for fail_duplicate_decl.carbon, which has a "Previous definition" note that points at the storage's parse node. --- toolchain/parser/parse_node_kind.def | 7 +- toolchain/parser/parser.cpp | 13 +-- toolchain/parser/parser_state.def | 7 -- .../basics/fail_paren_match_regression.carbon | 8 +- toolchain/parser/testdata/basics/var.carbon | 8 +- .../fail_infix_uneven_space_after.carbon | 6 +- .../fail_precedence_star_minus.carbon | 8 +- .../fail_precedence_star_star.carbon | 10 +- .../operators/fail_star_star_no_space.carbon | 8 +- .../testdata/operators/fixity_in_var.carbon | 10 +- .../parser/testdata/operators/infix.carbon | 8 +- .../testdata/operators/infix_no_space.carbon | 8 +- .../operators/infix_with_paren_after.carbon | 12 +- .../operators/infix_with_paren_before.carbon | 12 +- .../parser/testdata/operators/postfix.carbon | 6 +- .../operators/postfix_space_after_op.carbon | 6 +- .../parser/testdata/operators/prefix.carbon | 6 +- .../testdata/operators/prefix_no_space.carbon | 6 +- .../recover_infix_uneven_space_before.carbon | 8 +- .../operators/recover_postfix_space.carbon | 6 +- .../recover_postfix_space_before_comma.carbon | 16 +-- .../recover_postfix_space_in_call.carbon | 12 +- .../recover_postfix_space_surrounding.carbon | 6 +- .../operators/recover_prefix_space.carbon | 6 +- ...ver_prefix_uneven_space_with_assign.carbon | 6 +- .../testdata/struct/fail_comma_only.carbon | 6 +- .../struct/fail_comma_repeat_in_type.carbon | 6 +- .../struct/fail_comma_repeat_in_value.carbon | 6 +- .../testdata/struct/fail_dot_only.carbon | 6 +- .../struct/fail_dot_string_colon.carbon | 6 +- .../struct/fail_dot_string_equals.carbon | 6 +- .../struct/fail_extra_token_in_type.carbon | 14 +-- .../struct/fail_extra_token_in_value.carbon | 14 +-- .../struct/fail_identifier_colon.carbon | 6 +- .../struct/fail_identifier_equals.carbon | 6 +- .../struct/fail_identifier_only.carbon | 6 +- .../testdata/struct/fail_missing_type.carbon | 6 +- .../testdata/struct/fail_missing_value.carbon | 6 +- .../struct/fail_mix_type_and_value.carbon | 6 +- .../struct/fail_mix_value_and_type.carbon | 6 +- .../struct/fail_no_colon_or_equals.carbon | 6 +- .../struct/fail_type_no_designator.carbon | 6 +- .../parser/testdata/struct/no_entries.carbon | 6 +- .../testdata/struct/one_entry_no_comma.carbon | 14 +-- .../struct/one_entry_with_comma.carbon | 16 +-- .../parser/testdata/struct/two_entries.carbon | 24 ++-- .../parser/testdata/tuple/two_entries.carbon | 12 +- .../semantics_parse_tree_handler.cpp | 108 +++++++++++++----- .../semantics/semantics_parse_tree_handler.h | 20 +++- .../testdata/var/fail_duplicate_decl.carbon | 2 +- ...self.carbon => fail_init_with_self.carbon} | 6 +- .../testdata/var/global_lookup.carbon | 2 +- .../var/global_lookup_in_scope.carbon | 2 +- 53 files changed, 297 insertions(+), 242 deletions(-) rename toolchain/semantics/testdata/var/{todo_bad_init_with_self.carbon => fail_init_with_self.carbon} (86%) diff --git a/toolchain/parser/parse_node_kind.def b/toolchain/parser/parse_node_kind.def index 69488bcdf71a..e95c54c97352 100644 --- a/toolchain/parser/parse_node_kind.def +++ b/toolchain/parser/parse_node_kind.def @@ -104,11 +104,14 @@ CARBON_PARSE_NODE_KIND_CHILD_COUNT(PatternBinding, 2) // `var`: // VariableIntroducer // _external_: PatternBinding -// _external_: expression // optional VariableInitializer +// optional _external_: expression // VariableDeclaration +// +// The VariableInitializer and following expression are paired: either both will +// be present, or neither will. CARBON_PARSE_NODE_KIND_CHILD_COUNT(VariableIntroducer, 0) -CARBON_PARSE_NODE_KIND_CHILD_COUNT(VariableInitializer, 1) +CARBON_PARSE_NODE_KIND_CHILD_COUNT(VariableInitializer, 0) CARBON_PARSE_NODE_KIND_BRACKET(VariableDeclaration, VariableIntroducer) // An expression statement: diff --git a/toolchain/parser/parser.cpp b/toolchain/parser/parser.cpp index 65ae76458c92..1b7895c0bd58 100644 --- a/toolchain/parser/parser.cpp +++ b/toolchain/parser/parser.cpp @@ -1811,21 +1811,12 @@ auto Parser::HandleVarAfterPatternState() -> void { } } - if (PositionIs(TokenKind::Equal())) { - PushState(ParserState::VarAfterInitializer()); - ++position_; + if (auto equals = ConsumeIf(TokenKind::Equal())) { + AddLeafNode(ParseNodeKind::VariableInitializer(), *equals); PushState(ParserState::Expression()); - return; } } -auto Parser::HandleVarAfterInitializerState() -> void { - auto state = PopState(); - - AddNode(ParseNodeKind::VariableInitializer(), state.token, - state.subtree_start, state.has_error); -} - auto Parser::HandleVarFinishAsSemicolonState() -> void { auto state = PopState(); diff --git a/toolchain/parser/parser_state.def b/toolchain/parser/parser_state.def index 9bfae9ccb6ec..bd80db2150aa 100644 --- a/toolchain/parser/parser_state.def +++ b/toolchain/parser/parser_state.def @@ -560,17 +560,10 @@ CARBON_PARSER_STATE(VarAsFor) // // If `Equal`: // 1. Expression -// 2. VarAfterInitializer // Else: // (state done) CARBON_PARSER_STATE(VarAfterPattern) -// Handles `var` after the initializer, wrapping up its subtree. -// -// Always: -// (state done) -CARBON_PARSER_STATE(VarAfterInitializer) - // Handles `var` parsing at the end. // // Always: diff --git a/toolchain/parser/testdata/basics/fail_paren_match_regression.carbon b/toolchain/parser/testdata/basics/fail_paren_match_regression.carbon index ea41ed4f2a6a..0a36274d2e07 100644 --- a/toolchain/parser/testdata/basics/fail_paren_match_regression.carbon +++ b/toolchain/parser/testdata/basics/fail_paren_match_regression.carbon @@ -6,10 +6,10 @@ // RUN: %{not} %{carbon-run-parser} // CHECK:STDOUT: [ // CHECK:STDOUT: {kind: 'VariableIntroducer', text: 'var'}, -// CHECK:STDOUT: {kind: 'ParenExpressionOrTupleLiteralStart', text: '('}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'foo'}, -// CHECK:STDOUT: {kind: 'ParenExpression', text: ')', has_error: yes, subtree_size: 3}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 4}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'ParenExpressionOrTupleLiteralStart', text: '('}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'foo'}, +// CHECK:STDOUT: {kind: 'ParenExpression', text: ')', has_error: yes, subtree_size: 3}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: 'var', has_error: yes, subtree_size: 6}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/basics/var.carbon b/toolchain/parser/testdata/basics/var.carbon index f36318a7453e..78a48780606b 100644 --- a/toolchain/parser/testdata/basics/var.carbon +++ b/toolchain/parser/testdata/basics/var.carbon @@ -9,8 +9,8 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'v'}, // CHECK:STDOUT: {kind: 'Literal', text: 'i32'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'Literal', text: '0'}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 2}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'Literal', text: '0'}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 7}, // CHECK:STDOUT: {kind: 'VariableIntroducer', text: 'var'}, // CHECK:STDOUT: {kind: 'DeclaredName', text: 'w'}, @@ -26,8 +26,8 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 's'}, // CHECK:STDOUT: {kind: 'NameReference', text: 'String'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'Literal', text: '"hello"'}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 2}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'Literal', text: '"hello"'}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 7}, // CHECK:STDOUT: {kind: 'FunctionDefinition', text: '}', subtree_size: 13}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, diff --git a/toolchain/parser/testdata/operators/fail_infix_uneven_space_after.carbon b/toolchain/parser/testdata/operators/fail_infix_uneven_space_after.carbon index c146b0878ea4..ef68ea0f473f 100644 --- a/toolchain/parser/testdata/operators/fail_infix_uneven_space_after.carbon +++ b/toolchain/parser/testdata/operators/fail_infix_uneven_space_after.carbon @@ -9,9 +9,9 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'n'}, // CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, -// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, +// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', has_error: yes, subtree_size: 8}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/fail_precedence_star_minus.carbon b/toolchain/parser/testdata/operators/fail_precedence_star_minus.carbon index 0a96cf92909d..687a26593a1e 100644 --- a/toolchain/parser/testdata/operators/fail_precedence_star_minus.carbon +++ b/toolchain/parser/testdata/operators/fail_precedence_star_minus.carbon @@ -9,11 +9,11 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'n'}, // CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, -// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, // CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, -// CHECK:STDOUT: {kind: 'InfixOperator', text: '-', has_error: yes, subtree_size: 4}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 5}, +// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, +// CHECK:STDOUT: {kind: 'InfixOperator', text: '-', has_error: yes, subtree_size: 4}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 10}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/fail_precedence_star_star.carbon b/toolchain/parser/testdata/operators/fail_precedence_star_star.carbon index d7dabe615391..b47200927ba4 100644 --- a/toolchain/parser/testdata/operators/fail_precedence_star_star.carbon +++ b/toolchain/parser/testdata/operators/fail_precedence_star_star.carbon @@ -9,11 +9,11 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'n'}, // CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, -// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'p'}, -// CHECK:STDOUT: {kind: 'InfixOperator', text: '*', has_error: yes, subtree_size: 4}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 5}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, +// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'p'}, +// CHECK:STDOUT: {kind: 'InfixOperator', text: '*', has_error: yes, subtree_size: 4}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 10}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/fail_star_star_no_space.carbon b/toolchain/parser/testdata/operators/fail_star_star_no_space.carbon index 5a651428972d..c17042dac4f5 100644 --- a/toolchain/parser/testdata/operators/fail_star_star_no_space.carbon +++ b/toolchain/parser/testdata/operators/fail_star_star_no_space.carbon @@ -9,10 +9,10 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'n'}, // CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, -// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 4}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, +// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, +// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 3}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', has_error: yes, subtree_size: 9}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/fixity_in_var.carbon b/toolchain/parser/testdata/operators/fixity_in_var.carbon index 746621f8280c..0eaa545804c5 100644 --- a/toolchain/parser/testdata/operators/fixity_in_var.carbon +++ b/toolchain/parser/testdata/operators/fixity_in_var.carbon @@ -15,16 +15,16 @@ // CHECK:STDOUT: {kind: 'Literal', text: 'i32'}, // CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 4}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'p'}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 2}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'p'}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 8}, // CHECK:STDOUT: {kind: 'VariableIntroducer', text: 'var'}, // CHECK:STDOUT: {kind: 'DeclaredName', text: 't'}, // CHECK:STDOUT: {kind: 'NameReference', text: 'Type'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'Literal', text: 'i32'}, -// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'Literal', text: 'i32'}, +// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 8}, // CHECK:STDOUT: {kind: 'FunctionDefinition', text: '}', subtree_size: 22}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, diff --git a/toolchain/parser/testdata/operators/infix.carbon b/toolchain/parser/testdata/operators/infix.carbon index d4c5f6cf1395..c7c5a17cfe0a 100644 --- a/toolchain/parser/testdata/operators/infix.carbon +++ b/toolchain/parser/testdata/operators/infix.carbon @@ -9,10 +9,10 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'n'}, // CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, -// CHECK:STDOUT: {kind: 'InfixOperator', text: '*', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 4}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, +// CHECK:STDOUT: {kind: 'InfixOperator', text: '*', subtree_size: 3}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 9}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/infix_no_space.carbon b/toolchain/parser/testdata/operators/infix_no_space.carbon index 6f7ba1758dd3..cbc897f3791a 100644 --- a/toolchain/parser/testdata/operators/infix_no_space.carbon +++ b/toolchain/parser/testdata/operators/infix_no_space.carbon @@ -9,10 +9,10 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'n'}, // CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, -// CHECK:STDOUT: {kind: 'InfixOperator', text: '*', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 4}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, +// CHECK:STDOUT: {kind: 'InfixOperator', text: '*', subtree_size: 3}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 9}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/infix_with_paren_after.carbon b/toolchain/parser/testdata/operators/infix_with_paren_after.carbon index 3bc38635e724..dd38fd7a7240 100644 --- a/toolchain/parser/testdata/operators/infix_with_paren_after.carbon +++ b/toolchain/parser/testdata/operators/infix_with_paren_after.carbon @@ -9,12 +9,12 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'n'}, // CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'Literal', text: '3'}, -// CHECK:STDOUT: {kind: 'ParenExpressionOrTupleLiteralStart', text: '('}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, -// CHECK:STDOUT: {kind: 'ParenExpression', text: ')', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'InfixOperator', text: '*', subtree_size: 5}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 6}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'Literal', text: '3'}, +// CHECK:STDOUT: {kind: 'ParenExpressionOrTupleLiteralStart', text: '('}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, +// CHECK:STDOUT: {kind: 'ParenExpression', text: ')', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'InfixOperator', text: '*', subtree_size: 5}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 11}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/infix_with_paren_before.carbon b/toolchain/parser/testdata/operators/infix_with_paren_before.carbon index 36b4e783636f..9b6eb4cdc996 100644 --- a/toolchain/parser/testdata/operators/infix_with_paren_before.carbon +++ b/toolchain/parser/testdata/operators/infix_with_paren_before.carbon @@ -9,12 +9,12 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'n'}, // CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'ParenExpressionOrTupleLiteralStart', text: '('}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, -// CHECK:STDOUT: {kind: 'ParenExpression', text: ')', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'Literal', text: '3'}, -// CHECK:STDOUT: {kind: 'InfixOperator', text: '*', subtree_size: 5}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 6}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'ParenExpressionOrTupleLiteralStart', text: '('}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, +// CHECK:STDOUT: {kind: 'ParenExpression', text: ')', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'Literal', text: '3'}, +// CHECK:STDOUT: {kind: 'InfixOperator', text: '*', subtree_size: 5}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 11}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/postfix.carbon b/toolchain/parser/testdata/operators/postfix.carbon index b0b9d0756bfd..8cb331b888f6 100644 --- a/toolchain/parser/testdata/operators/postfix.carbon +++ b/toolchain/parser/testdata/operators/postfix.carbon @@ -9,9 +9,9 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'v'}, // CHECK:STDOUT: {kind: 'NameReference', text: 'Type'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, -// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, +// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 8}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/postfix_space_after_op.carbon b/toolchain/parser/testdata/operators/postfix_space_after_op.carbon index aedd45ed112c..c74b84d11707 100644 --- a/toolchain/parser/testdata/operators/postfix_space_after_op.carbon +++ b/toolchain/parser/testdata/operators/postfix_space_after_op.carbon @@ -9,9 +9,9 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'v'}, // CHECK:STDOUT: {kind: 'NameReference', text: 'Type'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, -// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, +// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 8}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/prefix.carbon b/toolchain/parser/testdata/operators/prefix.carbon index 202502074012..b70d5ad839c6 100644 --- a/toolchain/parser/testdata/operators/prefix.carbon +++ b/toolchain/parser/testdata/operators/prefix.carbon @@ -9,9 +9,9 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'n'}, // CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, -// CHECK:STDOUT: {kind: 'PrefixOperator', text: '-', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, +// CHECK:STDOUT: {kind: 'PrefixOperator', text: '-', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 8}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/prefix_no_space.carbon b/toolchain/parser/testdata/operators/prefix_no_space.carbon index a4d09df41efe..d6a0eaf754b2 100644 --- a/toolchain/parser/testdata/operators/prefix_no_space.carbon +++ b/toolchain/parser/testdata/operators/prefix_no_space.carbon @@ -9,9 +9,9 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'n'}, // CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, -// CHECK:STDOUT: {kind: 'PrefixOperator', text: '-', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, +// CHECK:STDOUT: {kind: 'PrefixOperator', text: '-', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 8}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/recover_infix_uneven_space_before.carbon b/toolchain/parser/testdata/operators/recover_infix_uneven_space_before.carbon index 4efdccc9df59..f722eac57004 100644 --- a/toolchain/parser/testdata/operators/recover_infix_uneven_space_before.carbon +++ b/toolchain/parser/testdata/operators/recover_infix_uneven_space_before.carbon @@ -9,10 +9,10 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'n'}, // CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, -// CHECK:STDOUT: {kind: 'InfixOperator', text: '*', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 4}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, +// CHECK:STDOUT: {kind: 'InfixOperator', text: '*', subtree_size: 3}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 9}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/recover_postfix_space.carbon b/toolchain/parser/testdata/operators/recover_postfix_space.carbon index ba0c2c9f8d52..59fd8457e506 100644 --- a/toolchain/parser/testdata/operators/recover_postfix_space.carbon +++ b/toolchain/parser/testdata/operators/recover_postfix_space.carbon @@ -9,9 +9,9 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'v'}, // CHECK:STDOUT: {kind: 'NameReference', text: 'Type'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, -// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, +// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 8}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/recover_postfix_space_before_comma.carbon b/toolchain/parser/testdata/operators/recover_postfix_space_before_comma.carbon index 4a6c2438b860..33b0c175beda 100644 --- a/toolchain/parser/testdata/operators/recover_postfix_space_before_comma.carbon +++ b/toolchain/parser/testdata/operators/recover_postfix_space_before_comma.carbon @@ -9,14 +9,14 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'n'}, // CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'F'}, -// CHECK:STDOUT: {kind: 'CallExpressionStart', text: '(', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, -// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'CallExpressionComma', text: ','}, -// CHECK:STDOUT: {kind: 'Literal', text: '0'}, -// CHECK:STDOUT: {kind: 'CallExpression', text: ')', subtree_size: 7}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 8}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'F'}, +// CHECK:STDOUT: {kind: 'CallExpressionStart', text: '(', subtree_size: 2}, +// CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, +// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, +// CHECK:STDOUT: {kind: 'CallExpressionComma', text: ','}, +// CHECK:STDOUT: {kind: 'Literal', text: '0'}, +// CHECK:STDOUT: {kind: 'CallExpression', text: ')', subtree_size: 7}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 13}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/recover_postfix_space_in_call.carbon b/toolchain/parser/testdata/operators/recover_postfix_space_in_call.carbon index 76e703d42139..f4fae68553cd 100644 --- a/toolchain/parser/testdata/operators/recover_postfix_space_in_call.carbon +++ b/toolchain/parser/testdata/operators/recover_postfix_space_in_call.carbon @@ -9,12 +9,12 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'n'}, // CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'F'}, -// CHECK:STDOUT: {kind: 'CallExpressionStart', text: '(', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, -// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'CallExpression', text: ')', subtree_size: 5}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 6}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'F'}, +// CHECK:STDOUT: {kind: 'CallExpressionStart', text: '(', subtree_size: 2}, +// CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, +// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, +// CHECK:STDOUT: {kind: 'CallExpression', text: ')', subtree_size: 5}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 11}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/recover_postfix_space_surrounding.carbon b/toolchain/parser/testdata/operators/recover_postfix_space_surrounding.carbon index a55a535675fc..59ff38131301 100644 --- a/toolchain/parser/testdata/operators/recover_postfix_space_surrounding.carbon +++ b/toolchain/parser/testdata/operators/recover_postfix_space_surrounding.carbon @@ -9,9 +9,9 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'v'}, // CHECK:STDOUT: {kind: 'NameReference', text: 'Type'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, -// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, +// CHECK:STDOUT: {kind: 'PostfixOperator', text: '*', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 8}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/recover_prefix_space.carbon b/toolchain/parser/testdata/operators/recover_prefix_space.carbon index 3d49f34055a0..68748c1a712a 100644 --- a/toolchain/parser/testdata/operators/recover_prefix_space.carbon +++ b/toolchain/parser/testdata/operators/recover_prefix_space.carbon @@ -9,9 +9,9 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'n'}, // CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, -// CHECK:STDOUT: {kind: 'PrefixOperator', text: '-', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, +// CHECK:STDOUT: {kind: 'PrefixOperator', text: '-', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 8}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/operators/recover_prefix_uneven_space_with_assign.carbon b/toolchain/parser/testdata/operators/recover_prefix_uneven_space_with_assign.carbon index f634575625a6..11707abd72a4 100644 --- a/toolchain/parser/testdata/operators/recover_prefix_uneven_space_with_assign.carbon +++ b/toolchain/parser/testdata/operators/recover_prefix_uneven_space_with_assign.carbon @@ -9,9 +9,9 @@ // CHECK:STDOUT: {kind: 'DeclaredName', text: 'n'}, // CHECK:STDOUT: {kind: 'Literal', text: 'i8'}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 3}, -// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, -// CHECK:STDOUT: {kind: 'PrefixOperator', text: '-', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'NameReference', text: 'n'}, +// CHECK:STDOUT: {kind: 'PrefixOperator', text: '-', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 8}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/fail_comma_only.carbon b/toolchain/parser/testdata/struct/fail_comma_only.carbon index 4bb95e4b158d..7aa31e240e20 100644 --- a/toolchain/parser/testdata/struct/fail_comma_only.carbon +++ b/toolchain/parser/testdata/struct/fail_comma_only.carbon @@ -12,9 +12,9 @@ // CHECK:STDOUT: {kind: 'StructComma', text: ','}, // CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 4}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 6}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 11}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/fail_comma_repeat_in_type.carbon b/toolchain/parser/testdata/struct/fail_comma_repeat_in_type.carbon index 845c8e8cab78..14194cc1449c 100644 --- a/toolchain/parser/testdata/struct/fail_comma_repeat_in_type.carbon +++ b/toolchain/parser/testdata/struct/fail_comma_repeat_in_type.carbon @@ -17,9 +17,9 @@ // CHECK:STDOUT: {kind: 'StructComma', text: ','}, // CHECK:STDOUT: {kind: 'StructTypeLiteral', text: '}', subtree_size: 9}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 11}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 16}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/fail_comma_repeat_in_value.carbon b/toolchain/parser/testdata/struct/fail_comma_repeat_in_value.carbon index 0623902a62f3..4de5fc08239d 100644 --- a/toolchain/parser/testdata/struct/fail_comma_repeat_in_value.carbon +++ b/toolchain/parser/testdata/struct/fail_comma_repeat_in_value.carbon @@ -17,9 +17,9 @@ // CHECK:STDOUT: {kind: 'StructComma', text: ','}, // CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 9}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 11}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 16}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/fail_dot_only.carbon b/toolchain/parser/testdata/struct/fail_dot_only.carbon index 4921fdeb9071..2a1300b7d402 100644 --- a/toolchain/parser/testdata/struct/fail_dot_only.carbon +++ b/toolchain/parser/testdata/struct/fail_dot_only.carbon @@ -13,9 +13,9 @@ // CHECK:STDOUT: {kind: 'StructFieldUnknown', text: '.', has_error: yes}, // CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 5}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 7}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 12}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/fail_dot_string_colon.carbon b/toolchain/parser/testdata/struct/fail_dot_string_colon.carbon index 948e0f8d26e5..cd3a7e7d890d 100644 --- a/toolchain/parser/testdata/struct/fail_dot_string_colon.carbon +++ b/toolchain/parser/testdata/struct/fail_dot_string_colon.carbon @@ -19,9 +19,9 @@ // CHECK:STDOUT: {kind: 'StructFieldType', text: ':', subtree_size: 4}, // CHECK:STDOUT: {kind: 'StructTypeLiteral', text: '}', subtree_size: 11}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 13}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 18}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/fail_dot_string_equals.carbon b/toolchain/parser/testdata/struct/fail_dot_string_equals.carbon index acaf4a4da71f..e511116b9ea5 100644 --- a/toolchain/parser/testdata/struct/fail_dot_string_equals.carbon +++ b/toolchain/parser/testdata/struct/fail_dot_string_equals.carbon @@ -19,9 +19,9 @@ // CHECK:STDOUT: {kind: 'StructFieldValue', text: '=', subtree_size: 4}, // CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 11}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 13}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 18}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/fail_extra_token_in_type.carbon b/toolchain/parser/testdata/struct/fail_extra_token_in_type.carbon index 94e568f7459e..6e79f65d6cc6 100644 --- a/toolchain/parser/testdata/struct/fail_extra_token_in_type.carbon +++ b/toolchain/parser/testdata/struct/fail_extra_token_in_type.carbon @@ -14,13 +14,13 @@ // CHECK:STDOUT: {kind: 'StructFieldType', text: ':', subtree_size: 4}, // CHECK:STDOUT: {kind: 'StructTypeLiteral', text: '}', has_error: yes, subtree_size: 6}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 8}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'DesignatedName', text: 'a'}, -// CHECK:STDOUT: {kind: 'StructFieldDesignator', text: '.', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'Literal', text: '0'}, -// CHECK:STDOUT: {kind: 'StructFieldValue', text: '=', subtree_size: 4}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 6}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 7}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'DesignatedName', text: 'a'}, +// CHECK:STDOUT: {kind: 'StructFieldDesignator', text: '.', subtree_size: 2}, +// CHECK:STDOUT: {kind: 'Literal', text: '0'}, +// CHECK:STDOUT: {kind: 'StructFieldValue', text: '=', subtree_size: 4}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 6}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 17}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/fail_extra_token_in_value.carbon b/toolchain/parser/testdata/struct/fail_extra_token_in_value.carbon index 4b41ad353fdd..901f0f1cf612 100644 --- a/toolchain/parser/testdata/struct/fail_extra_token_in_value.carbon +++ b/toolchain/parser/testdata/struct/fail_extra_token_in_value.carbon @@ -14,13 +14,13 @@ // CHECK:STDOUT: {kind: 'StructFieldType', text: ':', subtree_size: 4}, // CHECK:STDOUT: {kind: 'StructTypeLiteral', text: '}', subtree_size: 6}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 8}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'DesignatedName', text: 'a'}, -// CHECK:STDOUT: {kind: 'StructFieldDesignator', text: '.', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'Literal', text: '0'}, -// CHECK:STDOUT: {kind: 'StructFieldValue', text: '=', subtree_size: 4}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', has_error: yes, subtree_size: 6}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 7}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'DesignatedName', text: 'a'}, +// CHECK:STDOUT: {kind: 'StructFieldDesignator', text: '.', subtree_size: 2}, +// CHECK:STDOUT: {kind: 'Literal', text: '0'}, +// CHECK:STDOUT: {kind: 'StructFieldValue', text: '=', subtree_size: 4}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', has_error: yes, subtree_size: 6}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 17}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/fail_identifier_colon.carbon b/toolchain/parser/testdata/struct/fail_identifier_colon.carbon index 5ed7ff2e4928..fc9a6ede6349 100644 --- a/toolchain/parser/testdata/struct/fail_identifier_colon.carbon +++ b/toolchain/parser/testdata/struct/fail_identifier_colon.carbon @@ -11,9 +11,9 @@ // CHECK:STDOUT: {kind: 'StructFieldUnknown', text: 'a', has_error: yes}, // CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 3}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 5}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 10}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/fail_identifier_equals.carbon b/toolchain/parser/testdata/struct/fail_identifier_equals.carbon index 5c116f5c83a4..b2a77a300cdc 100644 --- a/toolchain/parser/testdata/struct/fail_identifier_equals.carbon +++ b/toolchain/parser/testdata/struct/fail_identifier_equals.carbon @@ -11,9 +11,9 @@ // CHECK:STDOUT: {kind: 'StructFieldUnknown', text: 'a', has_error: yes}, // CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 3}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 5}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 10}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/fail_identifier_only.carbon b/toolchain/parser/testdata/struct/fail_identifier_only.carbon index eb7d6412e8f4..28b4f2efa8e1 100644 --- a/toolchain/parser/testdata/struct/fail_identifier_only.carbon +++ b/toolchain/parser/testdata/struct/fail_identifier_only.carbon @@ -11,9 +11,9 @@ // CHECK:STDOUT: {kind: 'StructFieldUnknown', text: 'a', has_error: yes}, // CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 3}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 5}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 10}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/fail_missing_type.carbon b/toolchain/parser/testdata/struct/fail_missing_type.carbon index 3670e56c4389..96581d451729 100644 --- a/toolchain/parser/testdata/struct/fail_missing_type.carbon +++ b/toolchain/parser/testdata/struct/fail_missing_type.carbon @@ -13,9 +13,9 @@ // CHECK:STDOUT: {kind: 'StructFieldUnknown', text: ':', has_error: yes}, // CHECK:STDOUT: {kind: 'StructTypeLiteral', text: '}', subtree_size: 5}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 7}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 12}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/fail_missing_value.carbon b/toolchain/parser/testdata/struct/fail_missing_value.carbon index 3576fc72ff2f..c3967521f6dd 100644 --- a/toolchain/parser/testdata/struct/fail_missing_value.carbon +++ b/toolchain/parser/testdata/struct/fail_missing_value.carbon @@ -13,9 +13,9 @@ // CHECK:STDOUT: {kind: 'StructFieldUnknown', text: '=', has_error: yes}, // CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 5}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 7}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 12}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/fail_mix_type_and_value.carbon b/toolchain/parser/testdata/struct/fail_mix_type_and_value.carbon index 9425d5ce7179..54cddc59d01c 100644 --- a/toolchain/parser/testdata/struct/fail_mix_type_and_value.carbon +++ b/toolchain/parser/testdata/struct/fail_mix_type_and_value.carbon @@ -18,9 +18,9 @@ // CHECK:STDOUT: {kind: 'StructFieldUnknown', text: '.', has_error: yes}, // CHECK:STDOUT: {kind: 'StructTypeLiteral', text: '}', subtree_size: 10}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 12}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 17}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/fail_mix_value_and_type.carbon b/toolchain/parser/testdata/struct/fail_mix_value_and_type.carbon index 5482f957c0cd..3e7ada9d4a8a 100644 --- a/toolchain/parser/testdata/struct/fail_mix_value_and_type.carbon +++ b/toolchain/parser/testdata/struct/fail_mix_value_and_type.carbon @@ -16,9 +16,9 @@ // CHECK:STDOUT: {kind: 'StructFieldUnknown', text: 'b', has_error: yes}, // CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 8}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 10}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 15}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/fail_no_colon_or_equals.carbon b/toolchain/parser/testdata/struct/fail_no_colon_or_equals.carbon index b4de62031710..b384009fcdac 100644 --- a/toolchain/parser/testdata/struct/fail_no_colon_or_equals.carbon +++ b/toolchain/parser/testdata/struct/fail_no_colon_or_equals.carbon @@ -13,9 +13,9 @@ // CHECK:STDOUT: {kind: 'StructFieldUnknown', text: '.', has_error: yes}, // CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 5}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 7}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 12}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/fail_type_no_designator.carbon b/toolchain/parser/testdata/struct/fail_type_no_designator.carbon index 0ab5a76cc5e4..0a62c76ff23b 100644 --- a/toolchain/parser/testdata/struct/fail_type_no_designator.carbon +++ b/toolchain/parser/testdata/struct/fail_type_no_designator.carbon @@ -11,9 +11,9 @@ // CHECK:STDOUT: {kind: 'StructFieldUnknown', text: 'i32', has_error: yes}, // CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 3}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 5}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 10}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/no_entries.carbon b/toolchain/parser/testdata/struct/no_entries.carbon index 8c06a18459ff..c95dd1cae535 100644 --- a/toolchain/parser/testdata/struct/no_entries.carbon +++ b/toolchain/parser/testdata/struct/no_entries.carbon @@ -10,9 +10,9 @@ // CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, // CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 4}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 3}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 2}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 9}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/one_entry_no_comma.carbon b/toolchain/parser/testdata/struct/one_entry_no_comma.carbon index fde9f2ae4a38..6afd717fdb2d 100644 --- a/toolchain/parser/testdata/struct/one_entry_no_comma.carbon +++ b/toolchain/parser/testdata/struct/one_entry_no_comma.carbon @@ -14,13 +14,13 @@ // CHECK:STDOUT: {kind: 'StructFieldType', text: ':', subtree_size: 4}, // CHECK:STDOUT: {kind: 'StructTypeLiteral', text: '}', subtree_size: 6}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 8}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'DesignatedName', text: 'n'}, -// CHECK:STDOUT: {kind: 'StructFieldDesignator', text: '.', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'Literal', text: '4'}, -// CHECK:STDOUT: {kind: 'StructFieldValue', text: '=', subtree_size: 4}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 6}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 7}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'DesignatedName', text: 'n'}, +// CHECK:STDOUT: {kind: 'StructFieldDesignator', text: '.', subtree_size: 2}, +// CHECK:STDOUT: {kind: 'Literal', text: '4'}, +// CHECK:STDOUT: {kind: 'StructFieldValue', text: '=', subtree_size: 4}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 6}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 17}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/one_entry_with_comma.carbon b/toolchain/parser/testdata/struct/one_entry_with_comma.carbon index 5055feff7774..d42b20718031 100644 --- a/toolchain/parser/testdata/struct/one_entry_with_comma.carbon +++ b/toolchain/parser/testdata/struct/one_entry_with_comma.carbon @@ -15,14 +15,14 @@ // CHECK:STDOUT: {kind: 'StructComma', text: ','}, // CHECK:STDOUT: {kind: 'StructTypeLiteral', text: '}', subtree_size: 7}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 9}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'DesignatedName', text: 'n'}, -// CHECK:STDOUT: {kind: 'StructFieldDesignator', text: '.', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'Literal', text: '4'}, -// CHECK:STDOUT: {kind: 'StructFieldValue', text: '=', subtree_size: 4}, -// CHECK:STDOUT: {kind: 'StructComma', text: ','}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 7}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 8}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'DesignatedName', text: 'n'}, +// CHECK:STDOUT: {kind: 'StructFieldDesignator', text: '.', subtree_size: 2}, +// CHECK:STDOUT: {kind: 'Literal', text: '4'}, +// CHECK:STDOUT: {kind: 'StructFieldValue', text: '=', subtree_size: 4}, +// CHECK:STDOUT: {kind: 'StructComma', text: ','}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 7}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 19}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/struct/two_entries.carbon b/toolchain/parser/testdata/struct/two_entries.carbon index 4a09e28764e4..02867b71172e 100644 --- a/toolchain/parser/testdata/struct/two_entries.carbon +++ b/toolchain/parser/testdata/struct/two_entries.carbon @@ -19,18 +19,18 @@ // CHECK:STDOUT: {kind: 'StructFieldType', text: ':', subtree_size: 4}, // CHECK:STDOUT: {kind: 'StructTypeLiteral', text: '}', subtree_size: 11}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 13}, -// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, -// CHECK:STDOUT: {kind: 'DesignatedName', text: 'a'}, -// CHECK:STDOUT: {kind: 'StructFieldDesignator', text: '.', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'Literal', text: '1'}, -// CHECK:STDOUT: {kind: 'StructFieldValue', text: '=', subtree_size: 4}, -// CHECK:STDOUT: {kind: 'StructComma', text: ','}, -// CHECK:STDOUT: {kind: 'DesignatedName', text: 'b'}, -// CHECK:STDOUT: {kind: 'StructFieldDesignator', text: '.', subtree_size: 2}, -// CHECK:STDOUT: {kind: 'Literal', text: '2'}, -// CHECK:STDOUT: {kind: 'StructFieldValue', text: '=', subtree_size: 4}, -// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 11}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 12}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'StructLiteralOrStructTypeLiteralStart', text: '{'}, +// CHECK:STDOUT: {kind: 'DesignatedName', text: 'a'}, +// CHECK:STDOUT: {kind: 'StructFieldDesignator', text: '.', subtree_size: 2}, +// CHECK:STDOUT: {kind: 'Literal', text: '1'}, +// CHECK:STDOUT: {kind: 'StructFieldValue', text: '=', subtree_size: 4}, +// CHECK:STDOUT: {kind: 'StructComma', text: ','}, +// CHECK:STDOUT: {kind: 'DesignatedName', text: 'b'}, +// CHECK:STDOUT: {kind: 'StructFieldDesignator', text: '.', subtree_size: 2}, +// CHECK:STDOUT: {kind: 'Literal', text: '2'}, +// CHECK:STDOUT: {kind: 'StructFieldValue', text: '=', subtree_size: 4}, +// CHECK:STDOUT: {kind: 'StructLiteral', text: '}', subtree_size: 11}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 27}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/parser/testdata/tuple/two_entries.carbon b/toolchain/parser/testdata/tuple/two_entries.carbon index e4b018caca82..7c3fdbd77973 100644 --- a/toolchain/parser/testdata/tuple/two_entries.carbon +++ b/toolchain/parser/testdata/tuple/two_entries.carbon @@ -13,12 +13,12 @@ // CHECK:STDOUT: {kind: 'Literal', text: 'i32'}, // CHECK:STDOUT: {kind: 'TupleLiteral', text: ')', subtree_size: 5}, // CHECK:STDOUT: {kind: 'PatternBinding', text: ':', subtree_size: 7}, -// CHECK:STDOUT: {kind: 'ParenExpressionOrTupleLiteralStart', text: '('}, -// CHECK:STDOUT: {kind: 'Literal', text: '1'}, -// CHECK:STDOUT: {kind: 'TupleLiteralComma', text: ','}, -// CHECK:STDOUT: {kind: 'Literal', text: '2'}, -// CHECK:STDOUT: {kind: 'TupleLiteral', text: ')', subtree_size: 5}, -// CHECK:STDOUT: {kind: 'VariableInitializer', text: '=', subtree_size: 6}, +// CHECK:STDOUT: {kind: 'VariableInitializer', text: '='}, +// CHECK:STDOUT: {kind: 'ParenExpressionOrTupleLiteralStart', text: '('}, +// CHECK:STDOUT: {kind: 'Literal', text: '1'}, +// CHECK:STDOUT: {kind: 'TupleLiteralComma', text: ','}, +// CHECK:STDOUT: {kind: 'Literal', text: '2'}, +// CHECK:STDOUT: {kind: 'TupleLiteral', text: ')', subtree_size: 5}, // CHECK:STDOUT: {kind: 'VariableDeclaration', text: ';', subtree_size: 15}, // CHECK:STDOUT: {kind: 'FileEnd', text: ''}, // CHECK:STDOUT: ] diff --git a/toolchain/semantics/semantics_parse_tree_handler.cpp b/toolchain/semantics/semantics_parse_tree_handler.cpp index f321b5260a7c..06f7c4120ee0 100644 --- a/toolchain/semantics/semantics_parse_tree_handler.cpp +++ b/toolchain/semantics/semantics_parse_tree_handler.cpp @@ -25,10 +25,14 @@ class SemanticsParseTreeHandler::PrettyStackTraceNodeStack output << "node_stack_:\n"; for (int i = 0; i < static_cast(handler_->node_stack_.size()); ++i) { const auto& entry = handler_->node_stack_[i]; - output << "\t" << i << ".\t" - << handler_->parse_tree_->node_kind(entry.parse_node); - if (entry.result_id.is_valid()) { - output << " -> " << entry.result_id; + auto parse_node_kind = handler_->parse_tree_->node_kind(entry.parse_node); + output << "\t" << i << ".\t" << parse_node_kind; + if (parse_node_kind == ParseNodeKind::PatternBinding()) { + output << " -> " << entry.name_id; + } else { + if (entry.result_id.is_valid()) { + output << " -> " << entry.result_id; + } } output << "\n"; } @@ -93,18 +97,18 @@ auto SemanticsParseTreeHandler::AddNode(SemanticsNode node) -> SemanticsNodeId { auto SemanticsParseTreeHandler::BindName(ParseTree::Node name_node, SemanticsNodeId type_id, - SemanticsNodeId target_id) -> void { + SemanticsNodeId target_id) + -> SemanticsStringId { CARBON_CHECK(parse_tree_->node_kind(name_node) == ParseNodeKind::DeclaredName()) << parse_tree_->node_kind(name_node); auto name_str = parse_tree_->GetNodeText(name_node); auto name_id = semantics_->AddString(name_str); - auto bind_id = AddNode( - SemanticsNode::MakeBindName(name_node, type_id, name_id, target_id)); + AddNode(SemanticsNode::MakeBindName(name_node, type_id, name_id, target_id)); auto [it, inserted] = current_scope().names.insert(name_id); if (inserted) { - name_lookup_[name_id].push_back(bind_id); + name_lookup_[name_id].push_back(target_id); } else { CARBON_DIAGNOSTIC(NameRedefined, Error, "Redefining {0} in the same scope.", llvm::StringRef); @@ -116,6 +120,7 @@ auto SemanticsParseTreeHandler::BindName(ParseTree::Node name_node, .Note(prev_def.parse_node(), PreviousDefinition) .Emit(); } + return name_id; } auto SemanticsParseTreeHandler::Push(ParseTree::Node parse_node) -> void { @@ -123,7 +128,8 @@ auto SemanticsParseTreeHandler::Push(ParseTree::Node parse_node) -> void { << parse_tree_->node_kind(parse_node) << "\n"; CARBON_CHECK(node_stack_.size() < (1 << 20)) << "Excessive stack size: likely infinite loop"; - node_stack_.push_back({parse_node, SemanticsNodeId::MakeInvalid()}); + node_stack_.push_back( + {.parse_node = parse_node, .result_id = SemanticsNodeId::MakeInvalid()}); } auto SemanticsParseTreeHandler::Push(ParseTree::Node parse_node, @@ -134,7 +140,7 @@ auto SemanticsParseTreeHandler::Push(ParseTree::Node parse_node, CARBON_CHECK(node_stack_.size() < (1 << 20)) << "Excessive stack size: likely infinite loop"; auto node_id = AddNode(node); - node_stack_.push_back({parse_node, node_id}); + node_stack_.push_back({.parse_node = parse_node, .result_id = node_id}); } auto SemanticsParseTreeHandler::Push(ParseTree::Node parse_node, @@ -144,7 +150,19 @@ auto SemanticsParseTreeHandler::Push(ParseTree::Node parse_node, << "\n"; CARBON_CHECK(node_stack_.size() < (1 << 20)) << "Excessive stack size: likely infinite loop"; - node_stack_.push_back({parse_node, node_id}); + node_stack_.push_back({.parse_node = parse_node, .result_id = node_id}); +} + +auto SemanticsParseTreeHandler::Push(ParseTree::Node parse_node, + SemanticsStringId name_id) -> void { + CARBON_CHECK(parse_tree_->node_kind(parse_node) == + ParseNodeKind::PatternBinding()); + CARBON_VLOG() << "Push " << node_stack_.size() << ": " + << parse_tree_->node_kind(parse_node) << " -> " << name_id + << "\n"; + CARBON_CHECK(node_stack_.size() < (1 << 20)) + << "Excessive stack size: likely infinite loop"; + node_stack_.push_back({.parse_node = parse_node, .name_id = name_id}); } auto SemanticsParseTreeHandler::Pop(ParseNodeKind pop_parse_kind) -> void { @@ -566,21 +584,23 @@ auto SemanticsParseTreeHandler::HandleParenExpressionOrTupleLiteralStart( auto SemanticsParseTreeHandler::HandlePatternBinding(ParseTree::Node parse_node) -> void { - // Allocate storage. auto type = node_stack_.pop_back_val(); CARBON_CHECK(type.result_id.is_valid()); - auto storage_id = - AddNode(SemanticsNode::MakeVarStorage(parse_node, type.result_id)); // Get the name. auto name_node = node_stack_.pop_back_val().parse_node; - // Bind the name to storage. - BindName(name_node, type.result_id, storage_id); + // Allocate storage, linked to the name for error locations. + auto storage_id = + AddNode(SemanticsNode::MakeVarStorage(name_node, type.result_id)); - // If this node's result is used, it'll be for the storage address, so - // provide that. - Push(parse_node, storage_id); + // Bind the name to storage. + auto name_id = BindName(name_node, type.result_id, storage_id); + + // If this node's result is used, it'll be for either the name or the storage + // address. The storage address can be found through the name, so we push the + // name. + Push(parse_node, name_id); } auto SemanticsParseTreeHandler::HandlePostfixOperator( @@ -681,16 +701,30 @@ auto SemanticsParseTreeHandler::HandleTupleLiteralComma( auto SemanticsParseTreeHandler::HandleVariableDeclaration( ParseTree::Node parse_node) -> void { - auto init_id = PopWithResultIf(ParseNodeKind::VariableInitializer()); - auto storage_id = PopWithResult(ParseNodeKind::PatternBinding()); - if (init_id) { - auto storage_type = TryTypeConversion(parse_node, storage_id, *init_id, + auto last_child = node_stack_.pop_back_val(); + CARBON_CHECK(last_child.result_id.is_valid()); + + if (parse_tree_->node_kind(last_child.parse_node) != + ParseNodeKind::PatternBinding()) { + SemanticsNodeId init_id = last_child.result_id; + auto storage_id = PopWithResult(ParseNodeKind::VariableInitializer()); + + auto binding = node_stack_.pop_back_val(); + CARBON_CHECK(parse_tree_->node_kind(binding.parse_node) == + ParseNodeKind::PatternBinding()); + CARBON_CHECK(binding.name_id.is_valid()); + + // Restore the name now that the initializer is complete. + AddNameToLookup(binding.name_id, storage_id); + + auto storage_type = TryTypeConversion(parse_node, storage_id, init_id, /*can_convert_lhs=*/false); AddNode(SemanticsNode::MakeAssign(parse_node, storage_type, storage_id, - *init_id)); + init_id)); } + Pop(ParseNodeKind::VariableIntroducer()); - Push(parse_node, storage_id); + Push(parse_node); } auto SemanticsParseTreeHandler::HandleVariableIntroducer( @@ -701,8 +735,28 @@ auto SemanticsParseTreeHandler::HandleVariableIntroducer( auto SemanticsParseTreeHandler::HandleVariableInitializer( ParseTree::Node parse_node) -> void { - // The child is the expression; propagate it for the parent. - Push(parse_node, PopWithResult()); + // Temporarily remove name lookup entries added by the `var`. These will be + // restored by `VariableDeclaration`. + auto back = node_stack_.back(); + CARBON_CHECK(parse_tree_->node_kind(back.parse_node) == + ParseNodeKind::PatternBinding()) + << parse_tree_->node_kind(back.parse_node); + + // Save the storage ID. + auto it = name_lookup_.find(back.name_id); + CARBON_CHECK(it != name_lookup_.end()); + CARBON_CHECK(!it->second.empty()); + auto storage_id = it->second.back(); + + // Pop the name from lookup. + if (it->second.size() == 1) { + // Erase names that no longer resolve. + name_lookup_.erase(it); + } else { + it->second.pop_back(); + } + + Push(parse_node, storage_id); } auto SemanticsParseTreeHandler::HandleWhileCondition( diff --git a/toolchain/semantics/semantics_parse_tree_handler.h b/toolchain/semantics/semantics_parse_tree_handler.h index 884c137633f3..c1ca7fad7cae 100644 --- a/toolchain/semantics/semantics_parse_tree_handler.h +++ b/toolchain/semantics/semantics_parse_tree_handler.h @@ -59,8 +59,12 @@ class SemanticsParseTreeHandler { // An entry in node_stack_. struct NodeStackEntry { ParseTree::Node parse_node; - // The result_id may be invalid if there's no result. - SemanticsNodeId result_id; + union { + // The result_id may be invalid if there's no result. + SemanticsNodeId result_id; + // The name_id is provided for PatternBindings. + SemanticsStringId name_id; + }; }; static_assert(sizeof(NodeStackEntry) == 8, "Unexpected NodeStackEntry size"); @@ -76,9 +80,16 @@ class SemanticsParseTreeHandler { // Adds a node to the current block, returning the produced ID. auto AddNode(SemanticsNode node) -> SemanticsNodeId; + // Adds a name to name lookup. This is typically done through BindName, but + // can also be used to restore removed names. + auto AddNameToLookup(SemanticsStringId name_id, SemanticsNodeId storage_id) + -> void { + name_lookup_[name_id].push_back(storage_id); + } + // Binds a DeclaredName to a target node with the given type. auto BindName(ParseTree::Node name_node, SemanticsNodeId type_id, - SemanticsNodeId target_id) -> void; + SemanticsNodeId target_id) -> SemanticsStringId; // Pushes a parse tree node onto the stack. Used when there is no IR generated // by the node. @@ -91,6 +102,9 @@ class SemanticsParseTreeHandler { // Pushes a parse tree node onto the stack with an already-built node ID. auto Push(ParseTree::Node parse_node, SemanticsNodeId node_id) -> void; + // Pushes a PatternBinding parse tree node onto the stack with its name. + auto Push(ParseTree::Node parse_node, SemanticsStringId name_id) -> void; + // Pops the top of the stack, verifying that it's the expected kind. auto Pop(ParseNodeKind pop_parse_kind) -> void; diff --git a/toolchain/semantics/testdata/var/fail_duplicate_decl.carbon b/toolchain/semantics/testdata/var/fail_duplicate_decl.carbon index b784f4f82d72..d91218f158bf 100644 --- a/toolchain/semantics/testdata/var/fail_duplicate_decl.carbon +++ b/toolchain/semantics/testdata/var/fail_duplicate_decl.carbon @@ -28,7 +28,7 @@ // CHECK:STDOUT: node11 = VarStorage(): node2; // CHECK:STDOUT: node12 = BindName(str1, node11): node2; // CHECK:STDOUT: node13 = IntegerLiteral(int1): node2; -// CHECK:STDOUT: node14 = Assign(node11, node13): node2; +// CHECK:STDOUT: node14 = Assign(node7, node13): node2; // CHECK:STDOUT: }, // CHECK:STDOUT: node_blocks = { // CHECK:STDOUT: block0 = { diff --git a/toolchain/semantics/testdata/var/todo_bad_init_with_self.carbon b/toolchain/semantics/testdata/var/fail_init_with_self.carbon similarity index 86% rename from toolchain/semantics/testdata/var/todo_bad_init_with_self.carbon rename to toolchain/semantics/testdata/var/fail_init_with_self.carbon index 6b783dbf5902..bb3f11f3e56c 100644 --- a/toolchain/semantics/testdata/var/todo_bad_init_with_self.carbon +++ b/toolchain/semantics/testdata/var/fail_init_with_self.carbon @@ -3,7 +3,7 @@ // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception // // AUTOUPDATE -// RUN: %{carbon-run-semantics} +// RUN: %{not} %{carbon-run-semantics} // CHECK:STDOUT: cross_reference_irs.size == 1, // CHECK:STDOUT: integer_literals = { // CHECK:STDOUT: }, @@ -21,7 +21,7 @@ // CHECK:STDOUT: node6 = FunctionDefinition(node4, block1); // CHECK:STDOUT: node7 = VarStorage(): node2; // CHECK:STDOUT: node8 = BindName(str1, node7): node2; -// CHECK:STDOUT: node9 = Assign(node7, node8): node2; +// CHECK:STDOUT: node9 = Assign(node7, node1): node1; // CHECK:STDOUT: }, // CHECK:STDOUT: node_blocks = { // CHECK:STDOUT: block0 = { @@ -37,6 +37,6 @@ // CHECK:STDOUT: } fn Main() { - // TODO: This should fail with `x`... uninitialized? Not yet declared? + // CHECK:STDERR: {{.*}}/toolchain/semantics/testdata/var/fail_init_with_self.carbon:[[@LINE+1]]:16: Name x not found var x: i32 = x; } diff --git a/toolchain/semantics/testdata/var/global_lookup.carbon b/toolchain/semantics/testdata/var/global_lookup.carbon index a08f802139ad..b52c8d19b500 100644 --- a/toolchain/semantics/testdata/var/global_lookup.carbon +++ b/toolchain/semantics/testdata/var/global_lookup.carbon @@ -23,7 +23,7 @@ // CHECK:STDOUT: node7 = Assign(node4, node6): node2; // CHECK:STDOUT: node8 = VarStorage(): node2; // CHECK:STDOUT: node9 = BindName(str1, node8): node2; -// CHECK:STDOUT: node10 = Assign(node8, node5): node2; +// CHECK:STDOUT: node10 = Assign(node8, node4): node2; // CHECK:STDOUT: }, // CHECK:STDOUT: node_blocks = { // CHECK:STDOUT: block0 = { diff --git a/toolchain/semantics/testdata/var/global_lookup_in_scope.carbon b/toolchain/semantics/testdata/var/global_lookup_in_scope.carbon index 641673caa256..2b1427be98f3 100644 --- a/toolchain/semantics/testdata/var/global_lookup_in_scope.carbon +++ b/toolchain/semantics/testdata/var/global_lookup_in_scope.carbon @@ -27,7 +27,7 @@ // CHECK:STDOUT: node10 = FunctionDefinition(node8, block1); // CHECK:STDOUT: node11 = VarStorage(): node2; // CHECK:STDOUT: node12 = BindName(str2, node11): node2; -// CHECK:STDOUT: node13 = Assign(node11, node5): node2; +// CHECK:STDOUT: node13 = Assign(node11, node4): node2; // CHECK:STDOUT: }, // CHECK:STDOUT: node_blocks = { // CHECK:STDOUT: block0 = {