Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings

Commit 6209d8d

Browse filesBrowse files
chloestefantsovaCommit Queue
authored andcommitted
[cfe] Implement trivial context allocation strategy for local variables
Part of #61572 Change-Id: I7569168e6595e88e2bda25a122f3b238c188b381 Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/466080 Reviewed-by: Johnni Winther <johnniwinther@google.com> Commit-Queue: Chloe Stefantsova <cstefantsova@google.com>
1 parent 2574aba commit 6209d8d
Copy full SHA for 6209d8d
Expand file treeCollapse file tree

21 files changed

+709
-54
lines changed
Open diff view settings
Collapse file

‎pkg/front_end/lib/src/kernel/body_builder.dart‎

Copy file name to clipboardExpand all lines: pkg/front_end/lib/src/kernel/body_builder.dart
+34-24Lines changed: 34 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -619,7 +619,16 @@ class BodyBuilderImpl extends StackListenerImpl
619619

620620
@override
621621
void registerVariableAssignment(ExpressionVariable variable) {
622-
assignedVariables.write(variable);
622+
// TODO(cstefantsova): Always pass [variable] to [assignedVariables.write]
623+
// when [InferenceVisitorBase.flowAnalysis] will use
624+
// [InternalExpressionVariable] instead of [ExpressionVariable] (that is,
625+
// pass it for the `Variable` type parameter of [FlowAnalysis]).
626+
if (variable case InternalExpressionVariable variable) {
627+
assignedVariables.write(variable.astVariable);
628+
} else {
629+
// Coverage-ignore-block(suite): Not run.
630+
assignedVariables.write(variable);
631+
}
623632
}
624633

625634
@override
@@ -2586,10 +2595,15 @@ class BodyBuilderImpl extends StackListenerImpl
25862595

25872596
@override
25882597
void registerVariableRead(ExpressionVariable variable) {
2589-
if (!(variable is InternalExpressionVariable &&
2590-
(variable as InternalExpressionVariable).isLocalFunction) &&
2591-
!variable.isWildcard) {
2592-
assignedVariables.read(variable);
2598+
if (variable case InternalExpressionVariable variable) {
2599+
if (!variable.isLocalFunction && !variable.isWildcard) {
2600+
assignedVariables.read(variable.astVariable);
2601+
}
2602+
} else {
2603+
// Coverage-ignore-block(suite): Not run.
2604+
if (!variable.isWildcard) {
2605+
assignedVariables.read(variable);
2606+
}
25932607
}
25942608
}
25952609

@@ -3462,21 +3476,23 @@ class BodyBuilderImpl extends StackListenerImpl
34623476
name = createWildcardVariableName(wildcardVariableIndex);
34633477
wildcardVariableIndex++;
34643478
}
3465-
VariableInitialization variable;
3479+
VariableInitialization variableInitialization;
3480+
InternalExpressionVariable internalVariable;
34663481
if (isClosureContextLoweringEnabled) {
3467-
variable = new VariableInitialization(
3468-
variable: new InternalLocalVariable(
3469-
astVariable: new LocalVariable(
3470-
cosmeticName: name,
3471-
type: currentLocalVariableType,
3472-
),
3473-
forSyntheticToken: identifier.token.isSynthetic,
3474-
isImplicitlyTyped: currentLocalVariableType == null,
3475-
).asExpressionVariable,
3482+
internalVariable = new InternalLocalVariable(
3483+
astVariable: new LocalVariable(
3484+
cosmeticName: name,
3485+
type: currentLocalVariableType,
3486+
),
3487+
forSyntheticToken: identifier.token.isSynthetic,
3488+
isImplicitlyTyped: currentLocalVariableType == null,
3489+
);
3490+
variableInitialization = new VariableInitialization(
3491+
variable: internalVariable.asExpressionVariable,
34763492
initializer: initializer,
34773493
);
34783494
} else {
3479-
variable =
3495+
variableInitialization = internalVariable =
34803496
new VariableDeclarationImpl(
34813497
name,
34823498
forSyntheticToken: identifier.token.isSynthetic,
@@ -3493,8 +3509,8 @@ class BodyBuilderImpl extends StackListenerImpl
34933509
..fileOffset = identifier.nameOffset
34943510
..fileEqualsOffset = offsetForToken(equalsToken);
34953511
}
3496-
assignedVariables.declare(variable.variable);
3497-
push(variable);
3512+
assignedVariables.declare(internalVariable.astVariable);
3513+
push(variableInitialization);
34983514
}
34993515

35003516
@override
@@ -7763,12 +7779,6 @@ class BodyBuilderImpl extends StackListenerImpl
77637779
token.charOffset,
77647780
);
77657781

7766-
if (isClosureContextLoweringEnabled) {
7767-
// TODO(cstefantsova): Add function parameters to the scope.
7768-
function.scope = new Scope(contexts: [])
7769-
..fileOffset = function.fileOffset;
7770-
}
7771-
77727782
if (declaration is FunctionDeclaration) {
77737783
VariableDeclaration variable = declaration.variable;
77747784
if (annotations != null) {
Collapse file

‎pkg/front_end/lib/src/kernel/internal_ast.dart‎

Copy file name to clipboardExpand all lines: pkg/front_end/lib/src/kernel/internal_ast.dart
+83-3Lines changed: 83 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -902,7 +902,7 @@ class VariableDeclarationImpl extends VariableStatement
902902
}
903903
}
904904

905-
class InternalLocalVariable
905+
class InternalLocalVariable extends Node
906906
with InternalExpressionVariableMixin, DelegatingVariableMixin
907907
implements LocalVariable, InternalExpressionVariable {
908908
@override
@@ -923,6 +923,25 @@ class InternalLocalVariable
923923
this.forSyntheticToken = false,
924924
this.isLocalFunction = false,
925925
});
926+
927+
@override
928+
String toString() {
929+
return "InternalLocalVariable(${toStringInternal()})";
930+
}
931+
932+
@override
933+
// Coverage-ignore(suite): Not run.
934+
void toTextInternal(AstPrinter printer) {
935+
printer.writeExpressionVariable(astVariable);
936+
List<String> modifiers = [
937+
if (forSyntheticToken) "forSyntheticToken",
938+
if (isImplicitlyTyped) "isImplicitlyTyped",
939+
if (isLocalFunction) "isLocalFunction",
940+
];
941+
if (modifiers.isNotEmpty) {
942+
printer.write("[${modifiers.join(",")}]");
943+
}
944+
}
926945
}
927946

928947
mixin DelegatingVariableMixin on InternalExpressionVariableMixin
@@ -1107,6 +1126,65 @@ mixin DelegatingVariableMixin on InternalExpressionVariableMixin
11071126
@override
11081127
bool get isAssignable => astVariable.isAssignable;
11091128

1129+
@override
1130+
// Coverage-ignore(suite): Not run.
1131+
bool get hasIsFinal => astVariable.hasIsFinal;
1132+
1133+
@override
1134+
// Coverage-ignore(suite): Not run.
1135+
bool get hasIsConst => astVariable.hasIsConst;
1136+
1137+
@override
1138+
// Coverage-ignore(suite): Not run.
1139+
bool get hasIsLate => astVariable.hasIsLate;
1140+
1141+
@override
1142+
// Coverage-ignore(suite): Not run.
1143+
bool get hasIsInitializingFormal => astVariable.hasIsInitializingFormal;
1144+
1145+
@override
1146+
// Coverage-ignore(suite): Not run.
1147+
bool get hasIsSynthesized => astVariable.hasIsSynthesized;
1148+
1149+
@override
1150+
// Coverage-ignore(suite): Not run.
1151+
bool get hasIsHoisted => astVariable.hasIsHoisted;
1152+
1153+
@override
1154+
// Coverage-ignore(suite): Not run.
1155+
bool get hasHasDeclaredInitializer => astVariable.hasHasDeclaredInitializer;
1156+
1157+
@override
1158+
// Coverage-ignore(suite): Not run.
1159+
bool get hasIsCovariantByClass => astVariable.hasIsCovariantByClass;
1160+
1161+
@override
1162+
// Coverage-ignore(suite): Not run.
1163+
bool get hasIsRequired => astVariable.hasIsRequired;
1164+
1165+
@override
1166+
// Coverage-ignore(suite): Not run.
1167+
bool get hasIsCovariantByDeclaration =>
1168+
astVariable.hasIsCovariantByDeclaration;
1169+
1170+
@override
1171+
// Coverage-ignore(suite): Not run.
1172+
bool get hasIsLowered => astVariable.hasIsLowered;
1173+
1174+
@override
1175+
// Coverage-ignore(suite): Not run.
1176+
bool get hasIsWildcard => astVariable.hasIsWildcard;
1177+
1178+
@override
1179+
// Coverage-ignore(suite): Not run.
1180+
bool get hasIsSuperInitializingFormal =>
1181+
astVariable.hasIsSuperInitializingFormal;
1182+
1183+
@override
1184+
// Coverage-ignore(suite): Not run.
1185+
bool get hasIsErroneouslyInitialized =>
1186+
astVariable.hasIsErroneouslyInitialized;
1187+
11101188
@override
11111189
int get fileOffset {
11121190
throw new UnsupportedError("${this.runtimeType}");
@@ -1184,13 +1262,15 @@ mixin DelegatingVariableMixin on InternalExpressionVariableMixin
11841262
}
11851263

11861264
@override
1265+
// Coverage-ignore(suite): Not run.
11871266
String toStringInternal() {
1188-
throw new UnsupportedError("${this.runtimeType}");
1267+
return super.toStringInternal();
11891268
}
11901269

11911270
@override
1271+
// Coverage-ignore(suite): Not run.
11921272
String toText(AstTextStrategy strategy) {
1193-
throw new UnsupportedError("${this.runtimeType}");
1273+
return super.toText(strategy);
11941274
}
11951275

11961276
@override
Collapse file

‎pkg/front_end/lib/src/source/outline_builder.dart‎

Copy file name to clipboardExpand all lines: pkg/front_end/lib/src/source/outline_builder.dart
+1-1Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4742,8 +4742,8 @@ extension on MemberKind {
47424742
return false;
47434743
case MemberKind.NonStaticMethod:
47444744
case MemberKind.ExtensionTypeNonStaticMethod:
4745-
// TODO(eernst): Write a test such that this does run.
47464745
// Coverage-ignore(suite): Not run.
4746+
// TODO(eernst): Write a test such that this does run.
47474747
case MemberKind.AnonymousMethod:
47484748
// Coverage-ignore(suite): Not run.
47494749
// These can be inferred but cannot hold parameters so the cases are
Collapse file
+94Lines changed: 94 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,94 @@
1+
// Copyright (c) 2025, the Dart project authors. Please see the AUTHORS file
2+
// for details. All rights reserved. Use of this source code is governed by a
3+
// BSD-style license that can be found in the LICENSE file.
4+
5+
import 'package:kernel/ast.dart';
6+
import '../util/local_stack.dart';
7+
8+
abstract class ContextAllocationStrategy {
9+
LocalStack<ScopeProvider> _scopeProviderStack = new LocalStack<ScopeProvider>(
10+
<ScopeProvider>[],
11+
);
12+
ScopeProvider? get _currentScopeProvider => _scopeProviderStack.currentOrNull;
13+
14+
bool _enableDebugLogging = false;
15+
StringBuffer? _debugLog;
16+
17+
void _writeDebugLine(String line) {
18+
if (_enableDebugLogging) {
19+
// Coverage-ignore-block(suite): Not run.
20+
(_debugLog ??= new StringBuffer()).writeln(line);
21+
}
22+
}
23+
24+
// Coverage-ignore(suite): Not run.
25+
String _readDebugLog() {
26+
return _debugLog?.toString() ?? "";
27+
}
28+
29+
void enterScopeProvider(ScopeProvider scopeProvider) {
30+
assert(() {
31+
_writeDebugLine(
32+
"Entered ${scopeProvider.runtimeType} "
33+
"(id=${identityHashCode(scopeProvider)}).",
34+
);
35+
return true;
36+
}());
37+
_scopeProviderStack.push(scopeProvider);
38+
}
39+
40+
void exitScopeProvider(ScopeProvider scopeProvider) {
41+
assert(() {
42+
_writeDebugLine(
43+
"Exited ${scopeProvider.runtimeType} "
44+
"(id=${identityHashCode(scopeProvider)}).",
45+
);
46+
return true;
47+
}());
48+
assert(
49+
identical(_currentScopeProvider, scopeProvider),
50+
"Expected the current scope provider to be identical to the exited one: "
51+
"current=${_currentScopeProvider.runtimeType}, "
52+
"exited=${scopeProvider.runtimeType}."
53+
"\nDebug log:\n${_readDebugLog()}",
54+
);
55+
_scopeProviderStack.pop();
56+
}
57+
58+
VariableContext ensureVariableContextInCurrentScope({
59+
required CaptureKind captureKind,
60+
}) {
61+
assert(_currentScopeProvider != null);
62+
Scope scope = _currentScopeProvider!.scope ??= new Scope(contexts: []);
63+
for (VariableContext context in scope.contexts) {
64+
// Coverage-ignore-block(suite): Not run.
65+
if (context.captureKind == captureKind) {
66+
return context;
67+
}
68+
}
69+
VariableContext context = new VariableContext(
70+
captureKind: captureKind,
71+
variables: [],
72+
);
73+
scope.addContext(context);
74+
return context;
75+
}
76+
77+
void handleVariableInitialization(
78+
VariableInitialization variableInitialization, {
79+
required CaptureKind captureKind,
80+
});
81+
}
82+
83+
class TrivialContextAllocationStrategy extends ContextAllocationStrategy {
84+
@override
85+
void handleVariableInitialization(
86+
VariableInitialization variableInitialization, {
87+
required CaptureKind captureKind,
88+
}) {
89+
assert(_currentScopeProvider != null);
90+
ensureVariableContextInCurrentScope(
91+
captureKind: captureKind,
92+
).addVariable(variableInitialization.variable);
93+
}
94+
}

0 commit comments

Comments
0 (0)
Morty Proxy This is a proxified and sanitized view of the page, visit original site.