Don't create two parse nodes for each => token. (#7894)

Instead of producing two parse nodes in a row for each `=>` token,
produce just one.

Assisted-by: Gemini via Antigravity
This commit is contained in:
Richard Smith authored and GitHub committed 2026-10-06 21:43:36 +00:00
1 parent a5912b8b82
commit f83518bfd7
12 files changed
+12 -28

No files matched your search

+3 -5
View File
@@ -133,6 +133,9 @@ auto HandleParseNode(Context& context, Parse::LambdaDefinitionStartId node_id)
}
auto HandleParseNode(Context& context, Parse::LambdaId node_id) -> bool {
if (context.node_stack().PeekIs(Parse::NodeCategory::Expr)) {
return context.TODO(node_id, "terse lambda body");
}
auto function_id =
context.node_stack().Pop<Parse::NodeKind::LambdaDefinitionStart>();
CheckFunctionReturnOnFinish(context, node_id, function_id);
@@ -143,9 +146,4 @@ auto HandleParseNode(Context& context, Parse::LambdaId node_id) -> bool {
return true;
}
auto HandleParseNode(Context& context, Parse::TerseBodyArrowId node_id)
-> bool {
return context.TODO(node_id, "HandleTerseBodyArrow");
}
} // namespace Carbon::Check
-1
View File
@@ -546,7 +546,6 @@ class NodeStack {
case Parse::NodeKind::StructLiteralComma:
case Parse::NodeKind::StructFieldDesignator:
case Parse::NodeKind::StructTypeLiteralComma:
case Parse::NodeKind::TerseBodyArrow:
case Parse::NodeKind::TupleLiteralComma:
case Parse::NodeKind::TypeOfExprKeyword:
case Parse::NodeKind::TypeOfExprOpenParen:
@@ -57,9 +57,9 @@ library "[[@TEST_NAME]]";
// CHECK:STDERR: fn A => 0;
// CHECK:STDERR: ^~~~~~~
// CHECK:STDERR:
// CHECK:STDERR: fail_todo_arrow_body.carbon:[[@LINE+4]]:6: error: semantics TODO: `HandleTerseBodyArrow` [SemanticsTodo]
// CHECK:STDERR: fail_todo_arrow_body.carbon:[[@LINE+4]]:1: error: semantics TODO: `HandleFunctionTerseDefinition` [SemanticsTodo]
// CHECK:STDERR: fn A => 0;
// CHECK:STDERR: ^~
// CHECK:STDERR: ^~~~~~~~~~
// CHECK:STDERR:
fn A => 0;
+2 -2
View File
@@ -344,9 +344,9 @@ fn F() {
library "[[@TEST_NAME]]";
fn F() {
// CHECK:STDERR: fail_todo_terse_body.carbon:[[@LINE+4]]:16: error: semantics TODO: `HandleTerseBodyArrow` [SemanticsTodo]
// CHECK:STDERR: fail_todo_terse_body.carbon:[[@LINE+4]]:4: error: semantics TODO: `terse lambda body` [SemanticsTodo]
// CHECK:STDERR: (fn (x: i32) => x);
// CHECK:STDERR: ^~
// CHECK:STDERR: ^~~~~~~~~~~~~~~~
// CHECK:STDERR:
(fn (x: i32) => x);
}
@@ -48,7 +48,7 @@ fn Builtin() = "int.make_type_32";
// CHECK:STDOUT: "typeDefinitionProvider": true
// CHECK:STDOUT: }
// CHECK:STDOUT: }
// CHECK:STDOUT: }Content-Length: 482{{\r}}
// CHECK:STDOUT: }Content-Length: 490{{\r}}
// CHECK:STDOUT: {{\r}}
// CHECK:STDOUT: {
// CHECK:STDOUT: "jsonrpc": "2.0",
@@ -56,14 +56,14 @@ fn Builtin() = "int.make_type_32";
// CHECK:STDOUT: "params": {
// CHECK:STDOUT: "diagnostics": [
// CHECK:STDOUT: {
// CHECK:STDOUT: "message": "semantics TODO: `HandleTerseBodyArrow`",
// CHECK:STDOUT: "message": "semantics TODO: `HandleFunctionTerseDefinition`",
// CHECK:STDOUT: "range": {
// CHECK:STDOUT: "end": {
// CHECK:STDOUT: "character": 13,
// CHECK:STDOUT: "character": 17,
// CHECK:STDOUT: "line": 2
// CHECK:STDOUT: },
// CHECK:STDOUT: "start": {
// CHECK:STDOUT: "character": 11,
// CHECK:STDOUT: "character": 0,
// CHECK:STDOUT: "line": 2
// CHECK:STDOUT: }
// CHECK:STDOUT: },
-1
View File
@@ -63,7 +63,6 @@ auto HandleFunctionSignatureFinish(Context& context) -> void {
}
case Lex::TokenKind::EqualGreater: {
context.AddFunctionDefinitionStart(context.Consume(), state.has_error);
context.AddLeafNode(NodeKind::TerseBodyArrow, *(context.position() - 1));
context.PushState(state, StateKind::FunctionTerseBodyFinish);
context.PushStateForExpr(PrecedenceGroup::ForTopLevelExpr());
break;
+1 -3
View File
@@ -45,11 +45,9 @@ static auto ParseLambdaBody(Context& context, Context::State state,
bool has_return_type) -> void {
if (context.PositionIs(Lex::TokenKind::EqualGreater)) {
// Terse body `=> expr`
auto arrow_token = context.Consume();
context.AddNode(NodeKind::LambdaDefinitionStart, arrow_token,
context.AddNode(NodeKind::LambdaDefinitionStart, context.Consume(),
state.has_error);
state.has_error = false;
context.AddLeafNode(NodeKind::TerseBodyArrow, arrow_token);
context.PushState(state, StateKind::LambdaBodyFinish);
context.PushStateForExpr(PrecedenceGroup::ForTopLevelExpr());
} else if (context.PositionIs(Lex::TokenKind::OpenCurlyBrace)) {
-1
View File
@@ -203,7 +203,6 @@ CARBON_PARSE_NODE_KIND_DECLARATION(FunctionTerseDefinition)
CARBON_PARSE_NODE_KIND_DECLARATION(FunctionDecl)
CARBON_PARSE_NODE_KIND_DECLARATION(LambdaDefinitionStart)
CARBON_PARSE_NODE_KIND_DECLARATION(Lambda)
CARBON_PARSE_NODE_KIND_DECLARATION(TerseBodyArrow)
CARBON_PARSE_NODE_KIND_DECLARATION(BuiltinFunctionDefinitionStart)
CARBON_PARSE_NODE_KIND_DECLARATION(BuiltinName)
CARBON_PARSE_NODE_KIND_DECLARATION(BuiltinFunctionDefinition)
@@ -86,7 +86,6 @@ var b: auto = fn (x: i32 = 0) => x;
// CHECK:STDOUT: │ │ │ ├─DefaultValuePattern '='
// CHECK:STDOUT: │ │ ├─ExplicitParamList ')'
// CHECK:STDOUT: │ │ ╭─LambdaDefinitionStart '=>'
// CHECK:STDOUT: │ │ ├─TerseBodyArrow '=>'
// CHECK:STDOUT: │ │ ├─IdentifierNameExpr 'x'
// CHECK:STDOUT: │ ├─Lambda 'fn'
// CHECK:STDOUT: ├─VariableDecl ';'
-2
View File
@@ -23,7 +23,6 @@ fn G(x: i32) -> i32 => x;
// CHECK:STDOUT: │ │ ├─LetBindingPattern ':'
// CHECK:STDOUT: │ ├─ExplicitParamList ')'
// CHECK:STDOUT: │ ╭─FunctionDefinitionStart '=>'
// CHECK:STDOUT: │ ├─TerseBodyArrow '=>'
// CHECK:STDOUT: │ ├─IdentifierNameExpr 'x'
// CHECK:STDOUT: ├─FunctionTerseDefinition ';'
// CHECK:STDOUT: │ ╭─FunctionIntroducer 'fn'
@@ -37,7 +36,6 @@ fn G(x: i32) -> i32 => x;
// CHECK:STDOUT: │ │ ╭─IntTypeLiteral 'i32'
// CHECK:STDOUT: │ ├─ReturnType '->'
// CHECK:STDOUT: │ ╭─FunctionDefinitionStart '=>'
// CHECK:STDOUT: │ ├─TerseBodyArrow '=>'
// CHECK:STDOUT: │ ├─IdentifierNameExpr 'x'
// CHECK:STDOUT: ├─FunctionTerseDefinition ';'
// CHECK:STDOUT: ├─FileEnd ''
-1
View File
@@ -111,7 +111,6 @@ fn G() {
// CHECK:STDOUT: │ │ │ ├─LetBindingPattern ':'
// CHECK:STDOUT: │ │ ├─ExplicitParamList ')'
// CHECK:STDOUT: │ │ ╭─LambdaDefinitionStart '=>'
// CHECK:STDOUT: │ │ ├─TerseBodyArrow '=>'
// CHECK:STDOUT: │ │ ├─IdentifierNameExpr 'x'
// CHECK:STDOUT: │ ├─Lambda 'fn'
// CHECK:STDOUT: ├─VariableDecl ';'
-5
View File
@@ -627,7 +627,6 @@ struct FunctionTerseDefinition {
.bracketed_by = FunctionDefinitionStart::Kind});
FunctionDefinitionStartId signature;
TerseBodyArrowId arrow;
AnyExprId body;
Lex::SemiTokenIndex token;
};
@@ -776,9 +775,6 @@ struct VariablePattern {
using CodeBlockStart =
LeafNode<NodeKind::CodeBlockStart, Lex::OpenCurlyBraceTokenIndex>;
using TerseBodyArrow =
LeafNode<NodeKind::TerseBodyArrow, Lex::EqualGreaterTokenIndex>;
// A code block: `{ statement; statement; ... }`.
struct CodeBlock {
static constexpr auto Kind =
@@ -809,7 +805,6 @@ struct Lambda {
.bracketed_by = LambdaDefinitionStart::Kind});
LambdaDefinitionStartId signature;
std::optional<TerseBodyArrowId> arrow;
std::optional<AnyExprId> terse_body;
llvm::SmallVector<AnyStatementId> body;
// Use a generic token index because the token might be `}` or `fn`.