Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(702)

Unified Diff: pkg/compiler/lib/src/closure.dart

Issue 2387353002: Eagerly compute closure classes (Closed)
Patch Set: Add comments. Created 4 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « no previous file | pkg/compiler/lib/src/compiler.dart » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: pkg/compiler/lib/src/closure.dart
diff --git a/pkg/compiler/lib/src/closure.dart b/pkg/compiler/lib/src/closure.dart
index f9d431729deac978f979396b763357b61e1d1d67..e0c6826227443fe27a6bbcaa5f2f4558067b7e4f 100644
--- a/pkg/compiler/lib/src/closure.dart
+++ b/pkg/compiler/lib/src/closure.dart
@@ -23,32 +23,63 @@ import 'universe/world_builder.dart' show CodegenWorldBuilder;
import 'util/util.dart';
class ClosureTask extends CompilerTask {
- Map<Node, ClosureClassMap> closureMappingCache;
+ Map<Element, ClosureClassMap> _closureMappingCache =
+ <Element, ClosureClassMap>{};
Compiler compiler;
ClosureTask(Compiler compiler)
- : closureMappingCache = new Map<Node, ClosureClassMap>(),
- compiler = compiler,
+ : compiler = compiler,
super(compiler.measurer);
String get name => "Closure Simplifier";
DiagnosticReporter get reporter => compiler.reporter;
+ /// Returns the [ClosureClassMap] computed for [resolvedAst].
+ ClosureClassMap getClosureToClassMapping(ResolvedAst resolvedAst) {
+ return measure(() {
+ Element element = resolvedAst.element;
+ if (element.isGenerativeConstructorBody) {
+ ConstructorBodyElement constructorBody = element;
+ element = constructorBody.constructor;
+ }
+ ClosureClassMap closureClassMap = _closureMappingCache[element];
+ assert(invariant(resolvedAst.element, closureClassMap != null,
+ message: "No ClosureClassMap computed for ${element}."));
+ return closureClassMap;
+ });
+ }
+
+ /// Create [ClosureClassMap]s for all live members.
+ void createClosureClasses() {
+ compiler.enqueuer.resolution.processedElements
+ .forEach((AstElement element) {
+ ResolvedAst resolvedAst = element.resolvedAst;
+ if (element.isAbstract) return;
+ if (element.isField &&
+ !element.isInstanceMember &&
+ resolvedAst.body == null) {
+ // Skip top-level/static fields without an initializer.
+ return;
+ }
+ computeClosureToClassMapping(resolvedAst);
+ });
+ }
+
ClosureClassMap computeClosureToClassMapping(ResolvedAst resolvedAst) {
return measure(() {
Element element = resolvedAst.element;
+ ClosureClassMap cached = _closureMappingCache[element];
+ if (cached != null) return cached;
if (resolvedAst.kind != ResolvedAstKind.PARSED) {
- return new ClosureClassMap(null, null, null, new ThisLocal(element));
+ return _closureMappingCache[element] =
+ new ClosureClassMap(null, null, null, new ThisLocal(element));
}
return reporter.withCurrentElement(element.implementation, () {
Node node = resolvedAst.node;
TreeElements elements = resolvedAst.elements;
- ClosureClassMap cached = closureMappingCache[node];
- if (cached != null) return cached;
-
ClosureTranslator translator =
- new ClosureTranslator(compiler, elements, closureMappingCache);
+ new ClosureTranslator(compiler, elements, _closureMappingCache);
// The translator will store the computed closure-mappings inside the
// cache. One for given node and one for each nested closure.
@@ -57,7 +88,8 @@ class ClosureTask extends CompilerTask {
} else if (element.isSynthesized) {
reporter.internalError(
element, "Unexpected synthesized element: $element");
- return new ClosureClassMap(null, null, null, new ThisLocal(element));
+ _closureMappingCache[element] =
+ new ClosureClassMap(null, null, null, new ThisLocal(element));
} else {
assert(invariant(element, element.isField,
message: "Expected $element to be a field."));
@@ -69,26 +101,17 @@ class ClosureTask extends CompilerTask {
assert(invariant(element, element.isInstanceMember,
message: "Expected $element (${element
.runtimeType}) to be an instance field."));
- closureMappingCache[node] =
+ _closureMappingCache[element] =
new ClosureClassMap(null, null, null, new ThisLocal(element));
}
}
- assert(closureMappingCache[node] != null);
- return closureMappingCache[node];
+ assert(invariant(element, _closureMappingCache[element] != null,
+ message: "No ClosureClassMap computed for ${element}."));
+ return _closureMappingCache[element];
});
});
}
- ClosureClassMap getMappingForNestedFunction(FunctionExpression node) {
- return measure(() {
- ClosureClassMap nestedClosureData = closureMappingCache[node];
- if (nestedClosureData == null) {
- reporter.internalError(node, "No closure cache.");
- }
- return nestedClosureData;
- });
- }
-
void forgetElement(var closure) {
ClosureClassElement cls;
if (closure is ClosureFieldElement) {
@@ -526,7 +549,7 @@ class ClosureTranslator extends Visitor {
int boxedFieldCounter = 0;
bool inTryStatement = false;
- final Map<Node, ClosureClassMap> closureMappingCache;
+ final Map<Element, ClosureClassMap> closureMappingCache;
// Map of captured variables. Initially they will map to `null`. If
// a variable needs to be boxed then the scope declaring the variable
@@ -535,7 +558,7 @@ class ClosureTranslator extends Visitor {
new Map<Local, BoxFieldElement>();
// List of encountered closures.
- List<Expression> closures = <Expression>[];
+ List<LocalFunctionElement> closures = <LocalFunctionElement>[];
// The local variables that have been declared in the current scope.
List<LocalVariableElement> scopeVariables;
@@ -630,7 +653,7 @@ class ClosureTranslator extends Visitor {
// free variables to the boxed value. It also adds the field-elements to the
// class representing the closure.
void updateClosures() {
- for (Expression closure in closures) {
+ for (LocalFunctionElement closure in closures) {
// The captured variables that need to be stored in a field of the closure
// class.
Set<Local> fieldCaptures = new Set<Local>();
@@ -1074,7 +1097,7 @@ class ClosureTranslator extends Visitor {
executableContext = element;
if (insideClosure) {
closure = element;
- closures.add(node);
+ closures.add(closure);
closureData = globalizeClosure(node, closure);
} else {
outermostElement = element;
@@ -1084,7 +1107,10 @@ class ClosureTranslator extends Visitor {
}
closureData = new ClosureClassMap(null, null, null, thisElement);
}
- closureMappingCache[node] = closureData;
+ closureMappingCache[element.declaration] = closureData;
+ if (closureData.callElement != null) {
+ closureMappingCache[closureData.callElement] = closureData;
+ }
inNewScope(node, () {
DartType type = element.type;
« no previous file with comments | « no previous file | pkg/compiler/lib/src/compiler.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698