Chromium Code Reviews| OLD | NEW |
|---|---|
| 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 '../closure.dart' show BoxLocal, ThisLocal; | 9 import '../closure.dart' show BoxLocal, ThisLocal; |
| 10 import '../common.dart'; | 10 import '../common.dart'; |
| (...skipping 2150 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 2161 FunctionData data = _memberData[function.memberIndex]; | 2161 FunctionData data = _memberData[function.memberIndex]; |
| 2162 data.forEachParameter(this, f); | 2162 data.forEachParameter(this, f); |
| 2163 } | 2163 } |
| 2164 | 2164 |
| 2165 void _forEachConstructorBody( | 2165 void _forEachConstructorBody( |
| 2166 IndexedClass cls, void f(ConstructorBodyEntity member)) { | 2166 IndexedClass cls, void f(ConstructorBodyEntity member)) { |
| 2167 ClassEnv env = _classEnvs[cls.classIndex]; | 2167 ClassEnv env = _classEnvs[cls.classIndex]; |
| 2168 env.forEachConstructorBody(f); | 2168 env.forEachConstructorBody(f); |
| 2169 } | 2169 } |
| 2170 | 2170 |
| 2171 JRecordField _constructBoxedField( | |
| 2172 ir.VariableDeclaration variable, | |
| 2173 BoxLocal boxLocal, | |
| 2174 JClass container, | |
| 2175 Map<String, MemberEntity> memberMap, | |
| 2176 KernelToLocalsMap localsMap) { | |
| 2177 Local local = localsMap.getLocalVariable(variable); | |
| 2178 var boxedField = new JRecordField( | |
| 2179 local.name, _memberData.length, boxLocal, container, variable.isConst); | |
| 2180 _memberList.add(boxedField); | |
| 2181 _memberData.add(new ClosureFieldData(new ClosureMemberDefinition( | |
| 2182 boxedField, | |
| 2183 computeSourceSpanFromTreeNode(variable), | |
| 2184 MemberKind.closureField, | |
| 2185 variable))); | |
| 2186 memberMap[boxedField.name] = boxedField; | |
| 2187 | |
| 2188 return boxedField; | |
| 2189 } | |
| 2190 | |
| 2191 /// Make a container controlling access to records, that is, variables that | |
| 2192 /// are accessed in different scopes. This function creates the container as | |
|
sra1
2017/08/29 22:16:36
'container as and' ?
Emily Fortuna
2017/08/29 23:12:26
fixed
| |
| 2193 /// and returns a map of locals to the corresponding records created. | |
| 2194 Map<Local, JRecordField> makeRecordContainer( | |
| 2195 KernelScopeInfo info, MemberEntity member, KernelToLocalsMap localsMap) { | |
| 2196 Map<Local, JRecordField> boxedFields = {}; | |
| 2197 if (info.boxedVariables.isNotEmpty) { | |
| 2198 NodeBox box = info.capturedVariablesAccessor; | |
| 2199 | |
| 2200 var container = new JRecord(member.library, _classEnvs.length, box.name); | |
| 2201 _classList.add(container); | |
| 2202 Map<String, MemberEntity> memberMap = <String, MemberEntity>{}; | |
| 2203 _classEnvs.add(new RecordEnv(memberMap)); | |
| 2204 | |
| 2205 var containerData = new ClassData( | |
| 2206 null, | |
| 2207 new ClosureClassDefinition(container, | |
| 2208 computeSourceSpanFromTreeNode(getMemberDefinition(member).node))); | |
| 2209 containerData | |
| 2210 ..isMixinApplication = false | |
| 2211 ..thisType = new InterfaceType(container, const <DartType>[]) | |
| 2212 ..supertype = commonElements.objectType | |
| 2213 ..interfaces = const <InterfaceType>[]; | |
| 2214 var setBuilder = new _KernelOrderedTypeSetBuilder(this, container); | |
| 2215 _classData.add(containerData); | |
| 2216 containerData.orderedTypeSet = setBuilder.createOrderedTypeSet( | |
| 2217 containerData.supertype, const Link<InterfaceType>()); | |
| 2218 | |
| 2219 BoxLocal boxLocal = new BoxLocal(box.name, member); | |
| 2220 for (ir.VariableDeclaration variable in info.boxedVariables) { | |
| 2221 boxedFields[localsMap.getLocalVariable(variable)] = | |
| 2222 _constructBoxedField( | |
| 2223 variable, boxLocal, container, memberMap, localsMap); | |
| 2224 } | |
| 2225 } | |
| 2226 return boxedFields; | |
| 2227 } | |
| 2228 | |
| 2171 KernelClosureClass constructClosureClass( | 2229 KernelClosureClass constructClosureClass( |
| 2172 MemberEntity member, | 2230 MemberEntity member, |
| 2173 ir.FunctionNode node, | 2231 ir.FunctionNode node, |
| 2174 JLibrary enclosingLibrary, | 2232 JLibrary enclosingLibrary, |
| 2233 Map<Local, JRecordField> boxedCapturedVariables, | |
| 2175 KernelScopeInfo info, | 2234 KernelScopeInfo info, |
| 2176 ir.Location location, | 2235 ir.Location location, |
| 2177 KernelToLocalsMap localsMap, | 2236 KernelToLocalsMap localsMap, |
| 2178 InterfaceType supertype) { | 2237 InterfaceType supertype) { |
| 2179 String name = _computeClosureName(node); | 2238 String name = _computeClosureName(node); |
| 2180 JClass classEntity = | 2239 JClass classEntity = |
| 2181 new JClosureClass(enclosingLibrary, _classEnvs.length, name); | 2240 new JClosureClass(enclosingLibrary, _classEnvs.length, name); |
| 2182 _classList.add(classEntity); | 2241 _classList.add(classEntity); |
| 2183 Map<String, MemberEntity> memberMap = <String, MemberEntity>{}; | 2242 Map<String, MemberEntity> memberMap = <String, MemberEntity>{}; |
| 2184 _classEnvs.add(new ClosureClassEnv(memberMap)); | 2243 _classEnvs.add(new ClosureClassEnv(memberMap)); |
| (...skipping 19 matching lines...) Expand all Loading... | |
| 2204 if (node.parent is ir.FunctionDeclaration) { | 2263 if (node.parent is ir.FunctionDeclaration) { |
| 2205 ir.FunctionDeclaration parent = node.parent; | 2264 ir.FunctionDeclaration parent = node.parent; |
| 2206 closureEntity = localsMap.getLocalVariable(parent.variable); | 2265 closureEntity = localsMap.getLocalVariable(parent.variable); |
| 2207 } else if (node.parent is ir.FunctionExpression) { | 2266 } else if (node.parent is ir.FunctionExpression) { |
| 2208 closureEntity = new JLocal('', localsMap.currentMember); | 2267 closureEntity = new JLocal('', localsMap.currentMember); |
| 2209 } | 2268 } |
| 2210 Local thisLocal = | 2269 Local thisLocal = |
| 2211 info.hasThisLocal ? new ThisLocal(localsMap.currentMember) : null; | 2270 info.hasThisLocal ? new ThisLocal(localsMap.currentMember) : null; |
| 2212 | 2271 |
| 2213 KernelClosureClass cls = new KernelClosureClass.fromScopeInfo( | 2272 KernelClosureClass cls = new KernelClosureClass.fromScopeInfo( |
| 2214 classEntity, node, info, localsMap, closureEntity, thisLocal); | 2273 classEntity, |
| 2215 int i = 0; | 2274 node, |
| 2275 <Local, JRecordField>{}, | |
| 2276 info, | |
| 2277 localsMap, | |
| 2278 closureEntity, | |
| 2279 thisLocal); | |
| 2280 int fieldNumber = 0; | |
| 2216 for (ir.VariableDeclaration variable in info.freeVariables) { | 2281 for (ir.VariableDeclaration variable in info.freeVariables) { |
| 2217 // Make a corresponding field entity in this closure class for every | 2282 // Make a corresponding field entity in this closure class for every |
| 2218 // single freeVariable in the KernelScopeInfo.freeVariable. | 2283 // single freeVariable in the KernelScopeInfo.freeVariable. |
| 2219 _constructClosureFields(member, cls, memberMap, variable, i, | 2284 _constructClosureField( |
| 2220 info.capturedVariablesAccessor, localsMap); | 2285 member, |
| 2221 i++; | 2286 cls, |
| 2287 memberMap, | |
| 2288 variable, | |
| 2289 boxedCapturedVariables, | |
| 2290 fieldNumber, | |
| 2291 info.capturedVariablesAccessor, | |
| 2292 localsMap); | |
| 2293 fieldNumber++; | |
| 2222 } | 2294 } |
| 2223 | 2295 |
| 2224 FunctionEntity callMethod = cls.callMethod = new JClosureCallMethod( | 2296 FunctionEntity callMethod = cls.callMethod = new JClosureCallMethod( |
| 2225 _memberData.length, | 2297 _memberData.length, |
| 2226 cls, | 2298 cls, |
| 2227 _getParameterStructure(node), | 2299 _getParameterStructure(node), |
| 2228 _getAsyncMarker(node)); | 2300 _getAsyncMarker(node)); |
| 2229 _memberList.add(cls.callMethod); | 2301 _memberList.add(cls.callMethod); |
| 2230 | 2302 |
| 2231 _memberData.add(new ClosureFunctionData( | 2303 _memberData.add(new ClosureFunctionData( |
| 2232 new ClosureMemberDefinition(callMethod, closureData.definition.location, | 2304 new ClosureMemberDefinition(callMethod, closureData.definition.location, |
| 2233 MemberKind.closureCall, node.parent), | 2305 MemberKind.closureCall, node.parent), |
| 2234 getFunctionType(node), | 2306 getFunctionType(node), |
| 2235 node)); | 2307 node)); |
| 2236 memberMap[cls.callMethod.name] = cls.callMethod; | 2308 memberMap[cls.callMethod.name] = cls.callMethod; |
| 2237 return cls; | 2309 return cls; |
| 2238 } | 2310 } |
| 2239 | 2311 |
| 2240 _constructClosureFields( | 2312 _constructClosureField( |
| 2241 MemberEntity member, | 2313 MemberEntity member, |
| 2242 KernelClosureClass cls, | 2314 KernelClosureClass cls, |
| 2243 Map<String, MemberEntity> memberMap, | 2315 Map<String, MemberEntity> memberMap, |
| 2244 ir.VariableDeclaration variable, | 2316 ir.VariableDeclaration variable, |
| 2317 Map<Local, JRecordField> boxedCapturedVariables, | |
| 2245 int fieldNumber, | 2318 int fieldNumber, |
| 2246 NodeBox box, | 2319 NodeBox box, |
| 2247 KernelToLocalsMap localsMap) { | 2320 KernelToLocalsMap localsMap) { |
| 2248 // NOTE: This construction order may be slightly different than the | 2321 // NOTE: This construction order may be slightly different than the |
| 2249 // old Element version. The old version did all the boxed items and then | 2322 // old Element version. The old version did all the boxed items and then |
| 2250 // all the others. | 2323 // all the others. |
| 2251 Local capturedLocal = localsMap.getLocalVariable(variable); | 2324 Local capturedLocal = localsMap.getLocalVariable(variable); |
| 2252 if (cls.isBoxed(capturedLocal)) { | 2325 JRecordField record = boxedCapturedVariables[capturedLocal]; |
|
sra1
2017/08/29 22:16:36
maybe call this 'field'
Emily Fortuna
2017/08/29 23:12:26
done. yeah, there's some serious renaming I'll nee
| |
| 2253 FieldEntity boxedField = new JRecordField( | 2326 FieldEntity closureField = new JClosureField( |
| 2254 _getClosureVariableName(capturedLocal.name, fieldNumber), | 2327 _getClosureVariableName(capturedLocal.name, fieldNumber), |
| 2255 _memberData.length, | 2328 _memberData.length, |
| 2256 new BoxLocal(box.name, | 2329 cls, |
| 2257 localsMap.getLocalVariable(box.executableContext), member), | 2330 variable.isConst, |
| 2258 cls.closureClassEntity, | 2331 variable.isFinal || variable.isConst); |
| 2259 variable.isConst); | 2332 _memberList.add(closureField); |
| 2260 cls.localToFieldMap[capturedLocal] = boxedField; | 2333 _memberData.add(new ClosureFieldData(new ClosureMemberDefinition( |
| 2261 _memberList.add(boxedField); | 2334 cls.localToFieldMap[capturedLocal], |
| 2262 _memberData.add(new ClosureFieldData(new ClosureMemberDefinition( | 2335 computeSourceSpanFromTreeNode(variable), |
| 2263 boxedField, | 2336 MemberKind.closureField, |
| 2264 computeSourceSpanFromTreeNode(variable), | 2337 variable))); |
| 2265 MemberKind.closureField, | 2338 memberMap[closureField.name] = closureField; |
| 2266 variable))); | 2339 if (boxedCapturedVariables.containsKey(capturedLocal)) { |
| 2267 memberMap[boxedField.name] = boxedField; | 2340 cls.localToFieldMap[record.box] = closureField; |
| 2341 cls.boxedVariables[capturedLocal] = record; | |
| 2268 } else { | 2342 } else { |
| 2269 FieldEntity closureField = new JClosureField( | |
| 2270 _getClosureVariableName(capturedLocal.name, fieldNumber), | |
| 2271 _memberData.length, | |
| 2272 cls, | |
| 2273 variable.isConst, | |
| 2274 variable.isFinal || variable.isConst); | |
| 2275 cls.localToFieldMap[capturedLocal] = closureField; | 2343 cls.localToFieldMap[capturedLocal] = closureField; |
| 2276 _memberList.add(closureField); | |
| 2277 _memberData.add(new ClosureFieldData(new ClosureMemberDefinition( | |
| 2278 cls.localToFieldMap[capturedLocal], | |
| 2279 computeSourceSpanFromTreeNode(variable), | |
| 2280 MemberKind.closureField, | |
| 2281 variable))); | |
| 2282 memberMap[closureField.name] = closureField; | |
| 2283 } | 2344 } |
| 2284 } | 2345 } |
| 2285 | 2346 |
| 2286 // Returns a non-unique name for the given closure element. | 2347 // Returns a non-unique name for the given closure element. |
| 2287 String _computeClosureName(ir.TreeNode treeNode) { | 2348 String _computeClosureName(ir.TreeNode treeNode) { |
| 2288 var parts = <String>[]; | 2349 var parts = <String>[]; |
| 2289 if (treeNode is ir.Field && treeNode.name.name != "") { | 2350 if (treeNode is ir.Field && treeNode.name.name != "") { |
| 2290 parts.add(treeNode.name.name); | 2351 parts.add(treeNode.name.name); |
| 2291 } else { | 2352 } else { |
| 2292 parts.add('closure'); | 2353 parts.add('closure'); |
| (...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 2331 /// | 2392 /// |
| 2332 /// These names are not used in generated code, just as element name. | 2393 /// These names are not used in generated code, just as element name. |
| 2333 String _getClosureVariableName(String name, int id) { | 2394 String _getClosureVariableName(String name, int id) { |
| 2334 return "_captured_${name}_$id"; | 2395 return "_captured_${name}_$id"; |
| 2335 } | 2396 } |
| 2336 | 2397 |
| 2337 String getDeferredUri(ir.LibraryDependency node) { | 2398 String getDeferredUri(ir.LibraryDependency node) { |
| 2338 throw new UnimplementedError('JsKernelToElementMap.getDeferredUri'); | 2399 throw new UnimplementedError('JsKernelToElementMap.getDeferredUri'); |
| 2339 } | 2400 } |
| 2340 } | 2401 } |
| OLD | NEW |