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

Side by Side Diff: pkg/compiler/lib/src/kernel/element_map_impl.dart

Issue 2991903002: Add Closure call method to created closure class (Closed)
Patch Set: . Created 3 years, 4 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 unified diff | Download patch
« no previous file with comments | « pkg/compiler/lib/src/js_model/locals.dart ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2017, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2017, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 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. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 library dart2js.kernel.element_map; 5 library dart2js.kernel.element_map;
6 6
7 import 'package:kernel/ast.dart' as ir; 7 import 'package:kernel/ast.dart' as ir;
8 8
9 import '../common.dart'; 9 import '../common.dart';
10 import '../common/names.dart' show Identifiers; 10 import '../common/names.dart' show Identifiers;
11 import '../common/resolution.dart'; 11 import '../common/resolution.dart';
12 import '../compile_time_constants.dart'; 12 import '../compile_time_constants.dart';
13 import '../constants/constant_system.dart'; 13 import '../constants/constant_system.dart';
14 import '../constants/constructors.dart'; 14 import '../constants/constructors.dart';
15 import '../constants/evaluation.dart'; 15 import '../constants/evaluation.dart';
16 import '../constants/expressions.dart'; 16 import '../constants/expressions.dart';
17 import '../constants/values.dart'; 17 import '../constants/values.dart';
18 import '../common_elements.dart'; 18 import '../common_elements.dart';
19 import '../elements/elements.dart'; 19 import '../elements/elements.dart';
20 import '../elements/entities.dart'; 20 import '../elements/entities.dart';
21 import '../elements/entity_utils.dart' as utils;
21 import '../elements/names.dart'; 22 import '../elements/names.dart';
22 import '../elements/types.dart'; 23 import '../elements/types.dart';
23 import '../environment.dart'; 24 import '../environment.dart';
24 import '../frontend_strategy.dart'; 25 import '../frontend_strategy.dart';
25 import '../js_backend/backend_usage.dart'; 26 import '../js_backend/backend_usage.dart';
26 import '../js_backend/constant_system_javascript.dart'; 27 import '../js_backend/constant_system_javascript.dart';
27 import '../js_backend/interceptor_data.dart'; 28 import '../js_backend/interceptor_data.dart';
28 import '../js_backend/native_data.dart'; 29 import '../js_backend/native_data.dart';
29 import '../js_backend/no_such_method_registry.dart'; 30 import '../js_backend/no_such_method_registry.dart';
30 import '../js_backend/runtime_types.dart'; 31 import '../js_backend/runtime_types.dart';
(...skipping 1944 matching lines...) Expand 10 before | Expand all | Expand 10 after
1975 return; 1976 return;
1976 } 1977 }
1977 ConstructorData data = _memberData[constructor.memberIndex]; 1978 ConstructorData data = _memberData[constructor.memberIndex];
1978 if (data.constructorBody != null) { 1979 if (data.constructorBody != null) {
1979 f(data.constructorBody); 1980 f(data.constructorBody);
1980 } 1981 }
1981 }); 1982 });
1982 } 1983 }
1983 1984
1984 KernelClosureClass constructClosureClass( 1985 KernelClosureClass constructClosureClass(
1985 String name, 1986 MemberEntity member,
1987 ir.FunctionNode node,
1986 JLibrary enclosingLibrary, 1988 JLibrary enclosingLibrary,
1987 KernelScopeInfo info, 1989 KernelScopeInfo info,
1988 ir.Location location, 1990 ir.Location location,
1989 KernelToLocalsMap localsMap, 1991 KernelToLocalsMap localsMap,
1990 InterfaceType supertype) { 1992 InterfaceType supertype) {
1993 String name = _computeClosureName(node);
1991 KernelClosureClass cls = new KernelClosureClass.fromScopeInfo( 1994 KernelClosureClass cls = new KernelClosureClass.fromScopeInfo(
1992 name, _classEnvs.length, enclosingLibrary, info, location, localsMap); 1995 name, _classEnvs.length, enclosingLibrary, info, location, localsMap);
1993 _classList.add(cls); 1996 _classList.add(cls);
1994 _classEnvs.add(new ClassEnv.closureClass()); 1997 _classEnvs.add(new ClassEnv.closureClass());
1995 1998
1996 // Create a classData and set up the interfaces and subclass 1999 // Create a classData and set up the interfaces and subclass
1997 // relationships that _ensureSupertypes and _ensureThisAndRawType are doing 2000 // relationships that _ensureSupertypes and _ensureThisAndRawType are doing
1998 var closureData = 2001 var closureData =
1999 new ClassData(null, new ClosureClassDefinition(cls, cls.location)); 2002 new ClassData(null, new ClosureClassDefinition(cls, cls.location));
2000 closureData 2003 closureData
2001 ..isMixinApplication = false 2004 ..isMixinApplication = false
2002 ..thisType = 2005 ..thisType =
2003 closureData.rawType = new InterfaceType(cls, const/*<DartType>*/ []) 2006 closureData.rawType = new InterfaceType(cls, const/*<DartType>*/ [])
2004 ..supertype = supertype 2007 ..supertype = supertype
2005 ..interfaces = const <InterfaceType>[]; 2008 ..interfaces = const <InterfaceType>[];
2006 var setBuilder = new _KernelOrderedTypeSetBuilder(this, cls); 2009 var setBuilder = new _KernelOrderedTypeSetBuilder(this, cls);
2007 _classData.add(closureData); 2010 _classData.add(closureData);
2008 closureData.orderedTypeSet = setBuilder.createOrderedTypeSet( 2011 closureData.orderedTypeSet = setBuilder.createOrderedTypeSet(
2009 closureData.supertype, const Link<InterfaceType>()); 2012 closureData.supertype, const Link<InterfaceType>());
2010 2013
2011 int i = 0; 2014 int i = 0;
2012 for (ir.VariableDeclaration variable in info.freeVariables) { 2015 for (ir.VariableDeclaration variable in info.freeVariables) {
2013 // Make a corresponding field entity in this closure class for every 2016 // Make a corresponding field entity in this closure class for every
2014 // single freeVariable in the KernelScopeInfo.freeVariable. 2017 // single freeVariable in the KernelScopeInfo.freeVariable.
2015 _constructClosureFields(cls, variable, i, localsMap); 2018 _constructClosureFields(cls, variable, i, localsMap);
2016 i++; 2019 i++;
2017 } 2020 }
2018 2021
2022 cls.callMethod = new JClosureCallMethod(_memberData.length, cls, member);
2023 _memberList.add(cls.callMethod);
2024 _memberData.add(new MemberData(
2025 null,
2026 new ClosureMemberDefinition(
2027 member, cls.location, MemberKind.closureCall, node.parent)));
2028
2019 // TODO(efortuna): Does getMetadata get called in ClassData for this object? 2029 // TODO(efortuna): Does getMetadata get called in ClassData for this object?
2020 return cls; 2030 return cls;
2021 } 2031 }
2022 2032
2023 _constructClosureFields( 2033 _constructClosureFields(
2024 KernelClosureClass cls, 2034 KernelClosureClass cls,
2025 ir.VariableDeclaration variable, 2035 ir.VariableDeclaration variable,
2026 int fieldNumber, 2036 int fieldNumber,
2027 KernelToLocalsMap localsMap) { 2037 KernelToLocalsMap localsMap) {
2028 // NOTE: This construction order may be slightly different than the 2038 // NOTE: This construction order may be slightly different than the
2029 // old Element version. The old version did all the boxed items and then 2039 // old Element version. The old version did all the boxed items and then
2030 // all the others. 2040 // all the others.
2031 Local capturedLocal = localsMap.getLocalVariable(variable); 2041 Local capturedLocal = localsMap.getLocalVariable(variable);
2032 if (cls.isBoxed(capturedLocal)) { 2042 if (cls.isBoxed(capturedLocal)) {
2033 // TODO(efortuna): Coming soon. 2043 // TODO(efortuna): Coming soon.
2034 } else { 2044 } else {
2035 var closureField = new ClosureField( 2045 var closureField = new JClosureField(
2036 _getClosureVariableName(capturedLocal.name, fieldNumber), 2046 _getClosureVariableName(capturedLocal.name, fieldNumber),
2037 _memberData.length, 2047 _memberData.length,
2038 cls, 2048 cls,
2039 variable.isConst, 2049 variable.isConst,
2040 variable.isFinal || variable.isConst); 2050 variable.isFinal || variable.isConst);
2041 cls.localToFieldMap[capturedLocal] = closureField; 2051 cls.localToFieldMap[capturedLocal] = closureField;
2042 _memberList.add(closureField); 2052 _memberList.add(closureField);
2043 _memberData.add(new MemberData( 2053 _memberData.add(new MemberData(
2044 null, 2054 null,
2045 new ClosureMemberDefinition(cls.localToFieldMap[capturedLocal], 2055 new ClosureMemberDefinition(cls.localToFieldMap[capturedLocal],
2046 variable.location, MemberKind.closureField, variable))); 2056 variable.location, MemberKind.closureField, variable)));
2047 } 2057 }
2048 } 2058 }
2049 2059
2060 // Returns a non-unique name for the given closure element.
2061 String _computeClosureName(ir.TreeNode treeNode) {
2062 var parts = <String>[];
2063 if (treeNode is ir.Field && treeNode.name.name != "") {
2064 parts.add(treeNode.name.name);
2065 } else {
2066 parts.add('closure');
2067 }
2068 ir.TreeNode node = treeNode.parent;
2069 while (node != null &&
2070 (node is ir.Constructor ||
2071 node is ir.Class ||
2072 node is ir.FunctionNode ||
2073 node is ir.Procedure)) {
2074 // TODO(johnniwinther): Simplify computed names.
2075 if (node is ir.Constructor ||
2076 node.parent is ir.Constructor ||
2077 (node is ir.Procedure && node.kind == ir.ProcedureKind.Factory)) {
2078 FunctionEntity entity;
2079 if (node.parent is ir.Constructor) {
2080 entity = getConstructorBody(node);
2081 } else {
2082 entity = getMember(node);
2083 }
2084 parts.add(utils.reconstructConstructorName(entity));
2085 } else {
2086 String surroundingName = '';
2087 if (node is ir.Class) {
2088 surroundingName = Elements.operatorNameToIdentifier(node.name);
2089 } else if (node is ir.Procedure) {
2090 surroundingName = Elements.operatorNameToIdentifier(node.name.name);
2091 }
2092 parts.add(surroundingName);
2093 }
2094 // A generative constructors's parent is the class; the class name is
2095 // already part of the generative constructor's name.
2096 if (node is ir.Constructor) break;
2097 node = node.parent;
2098 }
2099 return parts.reversed.join('_');
2100 }
2101
2050 /// Generate a unique name for the [id]th closure field, with proposed name 2102 /// Generate a unique name for the [id]th closure field, with proposed name
2051 /// [name]. 2103 /// [name].
2052 /// 2104 ///
2053 /// The result is used as the name of [ClosureFieldElement]s, and must 2105 /// The result is used as the name of [ClosureFieldElement]s, and must
2054 /// therefore be unique to avoid breaking an invariant in the element model 2106 /// therefore be unique to avoid breaking an invariant in the element model
2055 /// (classes cannot declare multiple fields with the same name). 2107 /// (classes cannot declare multiple fields with the same name).
2056 /// 2108 ///
2057 /// Also, the names should be distinct from real field names to prevent 2109 /// Also, the names should be distinct from real field names to prevent
2058 /// clashes with selectors for those fields. 2110 /// clashes with selectors for those fields.
2059 /// 2111 ///
2060 /// These names are not used in generated code, just as element name. 2112 /// These names are not used in generated code, just as element name.
2061 String _getClosureVariableName(String name, int id) { 2113 String _getClosureVariableName(String name, int id) {
2062 return "_captured_${name}_$id"; 2114 return "_captured_${name}_$id";
2063 } 2115 }
2064 2116
2065 String getDeferredUri(ir.LibraryDependency node) { 2117 String getDeferredUri(ir.LibraryDependency node) {
2066 throw new UnimplementedError('JsKernelToElementMap.getDeferredUri'); 2118 throw new UnimplementedError('JsKernelToElementMap.getDeferredUri');
2067 } 2119 }
2068 } 2120 }
OLDNEW
« no previous file with comments | « pkg/compiler/lib/src/js_model/locals.dart ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698