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 import 'package:kernel/clone.dart'; | 8 import 'package:kernel/clone.dart'; |
9 import 'package:kernel/type_algebra.dart'; | 9 import 'package:kernel/type_algebra.dart'; |
10 | 10 |
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
55 | 55 |
56 /// Returns the constant initializer for [field]. | 56 /// Returns the constant initializer for [field]. |
57 ConstantValue getConstantFieldInitializer(FieldEntity field); | 57 ConstantValue getConstantFieldInitializer(FieldEntity field); |
58 | 58 |
59 /// Calls [f] for each parameter of [function] providing the type and name of | 59 /// Calls [f] for each parameter of [function] providing the type and name of |
60 /// the parameter and the [defaultValue] if the parameter is optional. | 60 /// the parameter and the [defaultValue] if the parameter is optional. |
61 void forEachParameter(FunctionEntity function, | 61 void forEachParameter(FunctionEntity function, |
62 void f(DartType type, String name, ConstantValue defaultValue)); | 62 void f(DartType type, String name, ConstantValue defaultValue)); |
63 } | 63 } |
64 | 64 |
65 abstract class KernelToElementMapBase extends KernelToElementMapBaseMixin {} | 65 class KernelToElementMapBase extends KernelToElementMapBaseMixin { |
66 | 66 final DiagnosticReporter reporter; |
67 /// Element builder used for creating elements and types corresponding to Kernel | |
68 /// IR nodes. | |
69 class KernelToElementMapImpl extends KernelToElementMapBase | |
70 with KernelToElementMapForBuildingMixin, KernelToElementMapForImpactMixin | |
71 implements KernelToWorldBuilder { | |
72 final Environment _environment; | |
73 CommonElements _commonElements; | 67 CommonElements _commonElements; |
74 native.BehaviorBuilder _nativeBehaviorBuilder; | |
75 final DiagnosticReporter reporter; | |
76 ElementEnvironment _elementEnvironment; | 68 ElementEnvironment _elementEnvironment; |
77 DartTypeConverter _typeConverter; | 69 DartTypeConverter _typeConverter; |
78 KernelConstantEnvironment _constantEnvironment; | 70 KernelConstantEnvironment _constantEnvironment; |
79 _KernelDartTypes _types; | |
80 | 71 |
81 /// Library environment. Used for fast lookup. | 72 /// Library environment. Used for fast lookup. |
82 _KEnv _env = new _KEnv(); | 73 _KEnv _env = new _KEnv(); |
83 | 74 |
84 /// List of library environments by `KLibrary.libraryIndex`. This is used for | 75 /// List of library environments by `KLibrary.libraryIndex`. This is used for |
85 /// fast lookup into library classes and members. | 76 /// fast lookup into library classes and members. |
86 List<_KLibraryEnv> _libraryEnvs = <_KLibraryEnv>[]; | 77 List<_KLibraryEnv> _libraryEnvs = <_KLibraryEnv>[]; |
87 | 78 |
88 /// List of class environments by `KClass.classIndex`. This is used for | 79 /// List of class environments by `KClass.classIndex`. This is used for |
89 /// fast lookup into class members. | 80 /// fast lookup into class members. |
90 List<_KClassEnv> _classEnvs = <_KClassEnv>[]; | 81 List<_KClassEnv> _classEnvs = <_KClassEnv>[]; |
91 | 82 |
92 Map<ir.Library, KLibrary> _libraryMap = <ir.Library, KLibrary>{}; | 83 Map<ir.Library, KLibrary> _libraryMap = <ir.Library, KLibrary>{}; |
93 Map<ir.Class, KClass> _classMap = <ir.Class, KClass>{}; | 84 Map<ir.Class, KClass> _classMap = <ir.Class, KClass>{}; |
94 Map<ir.TypeParameter, KTypeVariable> _typeVariableMap = | 85 Map<ir.TypeParameter, KTypeVariable> _typeVariableMap = |
95 <ir.TypeParameter, KTypeVariable>{}; | 86 <ir.TypeParameter, KTypeVariable>{}; |
96 | 87 |
97 List<_MemberData> _memberList = <_MemberData>[]; | 88 List<_MemberData> _memberList = <_MemberData>[]; |
98 | 89 |
99 Map<ir.Member, KConstructor> _constructorMap = <ir.Member, KConstructor>{}; | 90 Map<ir.Member, KConstructor> _constructorMap = <ir.Member, KConstructor>{}; |
100 Map<ir.Procedure, KFunction> _methodMap = <ir.Procedure, KFunction>{}; | 91 Map<ir.Procedure, KFunction> _methodMap = <ir.Procedure, KFunction>{}; |
101 Map<ir.Field, KField> _fieldMap = <ir.Field, KField>{}; | 92 Map<ir.Field, KField> _fieldMap = <ir.Field, KField>{}; |
102 | 93 |
103 Map<ir.TreeNode, KLocalFunction> _localFunctionMap = | 94 Map<ir.TreeNode, KLocalFunction> _localFunctionMap = |
104 <ir.TreeNode, KLocalFunction>{}; | 95 <ir.TreeNode, KLocalFunction>{}; |
105 | 96 |
106 KernelToElementMapImpl(this.reporter, this._environment) { | 97 KernelToElementMapBase(this.reporter, Environment environment) { |
107 _elementEnvironment = new KernelElementEnvironment(this); | 98 _elementEnvironment = new KernelElementEnvironment(this); |
108 _commonElements = new CommonElements(_elementEnvironment); | 99 _commonElements = new CommonElements(_elementEnvironment); |
109 _constantEnvironment = new KernelConstantEnvironment(this); | 100 _constantEnvironment = new KernelConstantEnvironment(this, environment); |
110 _nativeBehaviorBuilder = new KernelBehaviorBuilder(_commonElements); | |
111 _types = new _KernelDartTypes(this); | |
112 _typeConverter = new DartTypeConverter(this); | 101 _typeConverter = new DartTypeConverter(this); |
113 } | 102 } |
114 | 103 |
115 /// Adds libraries in [program] to the set of libraries. | 104 @override |
116 /// | 105 ElementEnvironment get elementEnvironment => _elementEnvironment; |
117 /// The main method of the first program is used as the main method for the | 106 |
118 /// compilation. | 107 @override |
119 void addProgram(ir.Program program) { | 108 CommonElements get commonElements => _commonElements; |
120 _env.addProgram(program); | |
121 } | |
122 | 109 |
123 KMethod get _mainFunction { | 110 KMethod get _mainFunction { |
124 return _env.mainMethod != null ? _getMethod(_env.mainMethod) : null; | 111 return _env.mainMethod != null ? _getMethod(_env.mainMethod) : null; |
125 } | 112 } |
126 | 113 |
127 KLibrary get _mainLibrary { | 114 KLibrary get _mainLibrary { |
128 return _env.mainMethod != null | 115 return _env.mainMethod != null |
129 ? _getLibrary(_env.mainMethod.enclosingLibrary) | 116 ? _getLibrary(_env.mainMethod.enclosingLibrary) |
130 : null; | 117 : null; |
131 } | 118 } |
132 | 119 |
133 Iterable<LibraryEntity> get _libraries { | 120 Iterable<LibraryEntity> get _libraries { |
134 if (_env.length != _libraryMap.length) { | 121 if (_env.length != _libraryMap.length) { |
135 // Create a [KLibrary] for each library. | 122 // Create a [KLibrary] for each library. |
136 _env.forEachLibrary((_KLibraryEnv env) { | 123 _env.forEachLibrary((_KLibraryEnv env) { |
137 _getLibrary(env.library, env); | 124 _getLibrary(env.library, env); |
138 }); | 125 }); |
139 } | 126 } |
140 return _libraryMap.values; | 127 return _libraryMap.values; |
141 } | 128 } |
142 | 129 |
143 @override | |
144 CommonElements get commonElements => _commonElements; | |
145 | |
146 @override | |
147 ElementEnvironment get elementEnvironment => _elementEnvironment; | |
148 | |
149 ConstantEnvironment get constantEnvironment => _constantEnvironment; | |
150 | |
151 DartTypes get types => _types; | |
152 | |
153 @override | |
154 native.BehaviorBuilder get nativeBehaviorBuilder => _nativeBehaviorBuilder; | |
155 | |
156 @override | |
157 ConstantValue computeConstantValue(ConstantExpression constant, | |
158 {bool requireConstant: true}) { | |
159 return _constantEnvironment.getConstantValue(constant); | |
160 } | |
161 | |
162 @override | |
163 ConstantValue getFieldConstantValue(ir.Field field) { | |
164 // TODO(johnniwinther): Cache the result in [_FieldData]. | |
165 return getConstantValue(field.initializer, | |
166 requireConstant: field.isConst, implicitNull: !field.isConst); | |
167 } | |
168 | |
169 LibraryEntity lookupLibrary(Uri uri) { | 130 LibraryEntity lookupLibrary(Uri uri) { |
170 _KLibraryEnv libraryEnv = _env.lookupLibrary(uri); | 131 _KLibraryEnv libraryEnv = _env.lookupLibrary(uri); |
171 if (libraryEnv == null) return null; | 132 if (libraryEnv == null) return null; |
172 return _getLibrary(libraryEnv.library, libraryEnv); | 133 return _getLibrary(libraryEnv.library, libraryEnv); |
173 } | 134 } |
174 | 135 |
175 KLibrary _getLibrary(ir.Library node, [_KLibraryEnv libraryEnv]) { | |
176 return _libraryMap.putIfAbsent(node, () { | |
177 Uri canonicalUri = node.importUri; | |
178 _libraryEnvs.add(libraryEnv ?? _env.lookupLibrary(canonicalUri)); | |
179 String name = node.name; | |
180 if (name == null) { | |
181 // Use the file name as script name. | |
182 String path = canonicalUri.path; | |
183 name = path.substring(path.lastIndexOf('/') + 1); | |
184 } | |
185 return new KLibrary(_libraryMap.length, name, canonicalUri); | |
186 }); | |
187 } | |
188 | |
189 String _getLibraryName(KLibrary library) { | 136 String _getLibraryName(KLibrary library) { |
190 _KLibraryEnv libraryEnv = _libraryEnvs[library.libraryIndex]; | 137 _KLibraryEnv libraryEnv = _libraryEnvs[library.libraryIndex]; |
191 return libraryEnv.library.name ?? ''; | 138 return libraryEnv.library.name ?? ''; |
192 } | 139 } |
193 | 140 |
194 MemberEntity lookupLibraryMember(KLibrary library, String name, | 141 MemberEntity lookupLibraryMember(KLibrary library, String name, |
195 {bool setter: false}) { | 142 {bool setter: false}) { |
196 _KLibraryEnv libraryEnv = _libraryEnvs[library.libraryIndex]; | 143 _KLibraryEnv libraryEnv = _libraryEnvs[library.libraryIndex]; |
197 ir.Member member = libraryEnv.lookupMember(name, setter: setter); | 144 ir.Member member = libraryEnv.lookupMember(name, setter: setter); |
198 return member != null ? getMember(member) : null; | 145 return member != null ? getMember(member) : null; |
(...skipping 30 matching lines...) Expand all Loading... |
229 ir.Member member = classEnv.lookupMember(name, setter: setter); | 176 ir.Member member = classEnv.lookupMember(name, setter: setter); |
230 return member != null ? getMember(member) : null; | 177 return member != null ? getMember(member) : null; |
231 } | 178 } |
232 | 179 |
233 ConstructorEntity lookupConstructor(KClass cls, String name) { | 180 ConstructorEntity lookupConstructor(KClass cls, String name) { |
234 _KClassEnv classEnv = _classEnvs[cls.classIndex]; | 181 _KClassEnv classEnv = _classEnvs[cls.classIndex]; |
235 ir.Member member = classEnv.lookupConstructor(name); | 182 ir.Member member = classEnv.lookupConstructor(name); |
236 return member != null ? getConstructor(member) : null; | 183 return member != null ? getConstructor(member) : null; |
237 } | 184 } |
238 | 185 |
| 186 @override |
| 187 InterfaceType createInterfaceType( |
| 188 ir.Class cls, List<ir.DartType> typeArguments) { |
| 189 return new InterfaceType(getClass(cls), getDartTypes(typeArguments)); |
| 190 } |
| 191 |
| 192 LibraryEntity getLibrary(ir.Library node) => _getLibrary(node); |
| 193 |
| 194 KLibrary _getLibrary(ir.Library node, [_KLibraryEnv libraryEnv]) { |
| 195 return _libraryMap.putIfAbsent(node, () { |
| 196 Uri canonicalUri = node.importUri; |
| 197 _libraryEnvs.add(libraryEnv ?? _env.lookupLibrary(canonicalUri)); |
| 198 String name = node.name; |
| 199 if (name == null) { |
| 200 // Use the file name as script name. |
| 201 String path = canonicalUri.path; |
| 202 name = path.substring(path.lastIndexOf('/') + 1); |
| 203 } |
| 204 return new KLibrary(_libraryMap.length, name, canonicalUri); |
| 205 }); |
| 206 } |
| 207 |
| 208 @override |
| 209 ClassEntity getClass(ir.Class node) => _getClass(node); |
| 210 |
239 KClass _getClass(ir.Class node, [_KClassEnv classEnv]) { | 211 KClass _getClass(ir.Class node, [_KClassEnv classEnv]) { |
240 return _classMap.putIfAbsent(node, () { | 212 return _classMap.putIfAbsent(node, () { |
241 KLibrary library = _getLibrary(node.enclosingLibrary); | 213 KLibrary library = _getLibrary(node.enclosingLibrary); |
242 if (classEnv == null) { | 214 if (classEnv == null) { |
243 classEnv = _libraryEnvs[library.libraryIndex].lookupClass(node.name); | 215 classEnv = _libraryEnvs[library.libraryIndex].lookupClass(node.name); |
244 } | 216 } |
245 _classEnvs.add(classEnv); | 217 _classEnvs.add(classEnv); |
246 return new KClass(library, _classMap.length, node.name, | 218 return new KClass(library, _classMap.length, node.name, |
247 isAbstract: node.isAbstract); | 219 isAbstract: node.isAbstract); |
248 }); | 220 }); |
249 } | 221 } |
250 | 222 |
251 Iterable<ConstantValue> _getClassMetadata(KClass cls) { | 223 InterfaceType _getSuperType(KClass cls) { |
252 return _classEnvs[cls.classIndex].getMetadata(this); | 224 _KClassEnv env = _classEnvs[cls.classIndex]; |
| 225 _ensureSupertypes(cls, env); |
| 226 return env.supertype; |
253 } | 227 } |
254 | 228 |
| 229 void _ensureThisAndRawType(KClass cls, _KClassEnv env) { |
| 230 if (env.thisType == null) { |
| 231 ir.Class node = env.cls; |
| 232 // TODO(johnniwinther): Add the type argument to the list literal when we |
| 233 // no longer use resolution types. |
| 234 if (node.typeParameters.isEmpty) { |
| 235 env.thisType = |
| 236 env.rawType = new InterfaceType(cls, const/*<DartType>*/ []); |
| 237 } else { |
| 238 env.thisType = new InterfaceType( |
| 239 cls, |
| 240 new List/*<DartType>*/ .generate(node.typeParameters.length, |
| 241 (int index) { |
| 242 return new TypeVariableType( |
| 243 _getTypeVariable(node.typeParameters[index])); |
| 244 })); |
| 245 env.rawType = new InterfaceType( |
| 246 cls, |
| 247 new List/*<DartType>*/ .filled( |
| 248 node.typeParameters.length, const DynamicType())); |
| 249 } |
| 250 } |
| 251 } |
| 252 |
| 253 TypeVariableEntity getTypeVariable(ir.TypeParameter node) => |
| 254 _getTypeVariable(node); |
| 255 |
255 KTypeVariable _getTypeVariable(ir.TypeParameter node) { | 256 KTypeVariable _getTypeVariable(ir.TypeParameter node) { |
256 return _typeVariableMap.putIfAbsent(node, () { | 257 return _typeVariableMap.putIfAbsent(node, () { |
257 if (node.parent is ir.Class) { | 258 if (node.parent is ir.Class) { |
258 ir.Class cls = node.parent; | 259 ir.Class cls = node.parent; |
259 int index = cls.typeParameters.indexOf(node); | 260 int index = cls.typeParameters.indexOf(node); |
260 return new KTypeVariable(_getClass(cls), node.name, index); | 261 return new KTypeVariable(_getClass(cls), node.name, index); |
261 } | 262 } |
262 if (node.parent is ir.FunctionNode) { | 263 if (node.parent is ir.FunctionNode) { |
263 ir.FunctionNode func = node.parent; | 264 ir.FunctionNode func = node.parent; |
264 int index = func.typeParameters.indexOf(node); | 265 int index = func.typeParameters.indexOf(node); |
265 if (func.parent is ir.Constructor) { | 266 if (func.parent is ir.Constructor) { |
266 ir.Constructor constructor = func.parent; | 267 ir.Constructor constructor = func.parent; |
267 ir.Class cls = constructor.enclosingClass; | 268 ir.Class cls = constructor.enclosingClass; |
268 return _getTypeVariable(cls.typeParameters[index]); | 269 return _getTypeVariable(cls.typeParameters[index]); |
269 } | 270 } |
270 if (func.parent is ir.Procedure) { | 271 if (func.parent is ir.Procedure) { |
271 ir.Procedure procedure = func.parent; | 272 ir.Procedure procedure = func.parent; |
272 if (procedure.kind == ir.ProcedureKind.Factory) { | 273 if (procedure.kind == ir.ProcedureKind.Factory) { |
273 ir.Class cls = procedure.enclosingClass; | 274 ir.Class cls = procedure.enclosingClass; |
274 return _getTypeVariable(cls.typeParameters[index]); | 275 return _getTypeVariable(cls.typeParameters[index]); |
275 } else { | 276 } else { |
276 return new KTypeVariable(_getMethod(procedure), node.name, index); | 277 return new KTypeVariable(_getMethod(procedure), node.name, index); |
277 } | 278 } |
278 } | 279 } |
279 } | 280 } |
280 throw new UnsupportedError('Unsupported type parameter type node $node.'); | 281 throw new UnsupportedError('Unsupported type parameter type node $node.'); |
281 }); | 282 }); |
282 } | 283 } |
283 | 284 |
284 ParameterStructure _getParameterStructure(ir.FunctionNode node) { | 285 void _ensureSupertypes(KClass cls, _KClassEnv env) { |
285 // TODO(johnniwinther): Cache the computed function type. | 286 if (env.orderedTypeSet == null) { |
286 int requiredParameters = node.requiredParameterCount; | 287 _ensureThisAndRawType(cls, env); |
287 int positionalParameters = node.positionalParameters.length; | 288 |
288 List<String> namedParameters = | 289 ir.Class node = env.cls; |
289 node.namedParameters.map((p) => p.name).toList()..sort(); | 290 |
290 return new ParameterStructure( | 291 if (node.supertype == null) { |
291 requiredParameters, positionalParameters, namedParameters); | 292 env.orderedTypeSet = new OrderedTypeSet.singleton(env.thisType); |
| 293 env.isMixinApplication = false; |
| 294 env.interfaces = const <InterfaceType>[]; |
| 295 } else { |
| 296 InterfaceType processSupertype(ir.Supertype node) { |
| 297 InterfaceType type = _typeConverter.visitSupertype(node); |
| 298 KClass superclass = type.element; |
| 299 _KClassEnv env = _classEnvs[superclass.classIndex]; |
| 300 _ensureSupertypes(superclass, env); |
| 301 return type; |
| 302 } |
| 303 |
| 304 env.supertype = processSupertype(node.supertype); |
| 305 LinkBuilder<InterfaceType> linkBuilder = |
| 306 new LinkBuilder<InterfaceType>(); |
| 307 if (node.mixedInType != null) { |
| 308 env.isMixinApplication = true; |
| 309 linkBuilder |
| 310 .addLast(env.mixedInType = processSupertype(node.mixedInType)); |
| 311 } else { |
| 312 env.isMixinApplication = false; |
| 313 } |
| 314 node.implementedTypes.forEach((ir.Supertype supertype) { |
| 315 linkBuilder.addLast(processSupertype(supertype)); |
| 316 }); |
| 317 Link<InterfaceType> interfaces = linkBuilder.toLink(); |
| 318 OrderedTypeSetBuilder setBuilder = |
| 319 new _KernelOrderedTypeSetBuilder(this, cls); |
| 320 env.orderedTypeSet = |
| 321 setBuilder.createOrderedTypeSet(env.supertype, interfaces); |
| 322 env.interfaces = new List<InterfaceType>.from(interfaces.toList()); |
| 323 } |
| 324 } |
292 } | 325 } |
293 | 326 |
| 327 @override |
| 328 MemberEntity getMember(ir.Member node) { |
| 329 if (node is ir.Field) { |
| 330 return _getField(node); |
| 331 } else if (node is ir.Constructor) { |
| 332 return _getConstructor(node); |
| 333 } else if (node is ir.Procedure) { |
| 334 if (node.kind == ir.ProcedureKind.Factory) { |
| 335 return _getConstructor(node); |
| 336 } else { |
| 337 return _getMethod(node); |
| 338 } |
| 339 } |
| 340 throw new UnsupportedError("Unexpected member: $node"); |
| 341 } |
| 342 |
| 343 MemberEntity getSuperMember(ir.Member context, ir.Name name, ir.Member target, |
| 344 {bool setter: false}) { |
| 345 if (target != null) { |
| 346 return getMember(target); |
| 347 } |
| 348 KClass cls = getMember(context).enclosingClass; |
| 349 KClass superclass = _getSuperType(cls)?.element; |
| 350 while (superclass != null) { |
| 351 _KClassEnv env = _classEnvs[superclass.classIndex]; |
| 352 ir.Member superMember = env.lookupMember(name.name, setter: setter); |
| 353 if (superMember != null) { |
| 354 return getMember(superMember); |
| 355 } |
| 356 superclass = _getSuperType(superclass)?.element; |
| 357 } |
| 358 throw new SpannableAssertionFailure( |
| 359 cls, "No super method member found for ${name} in $cls."); |
| 360 } |
| 361 |
| 362 @override |
| 363 ConstructorEntity getConstructor(ir.Member node) => _getConstructor(node); |
| 364 |
294 KConstructor _getConstructor(ir.Member node) { | 365 KConstructor _getConstructor(ir.Member node) { |
295 return _constructorMap.putIfAbsent(node, () { | 366 return _constructorMap.putIfAbsent(node, () { |
296 int memberIndex = _memberList.length; | 367 int memberIndex = _memberList.length; |
297 KConstructor constructor; | 368 KConstructor constructor; |
298 KClass enclosingClass = _getClass(node.enclosingClass); | 369 KClass enclosingClass = _getClass(node.enclosingClass); |
299 Name name = getName(node.name); | 370 Name name = getName(node.name); |
300 bool isExternal = node.isExternal; | 371 bool isExternal = node.isExternal; |
301 | 372 |
302 ir.FunctionNode functionNode; | 373 ir.FunctionNode functionNode; |
303 if (node is ir.Constructor) { | 374 if (node is ir.Constructor) { |
(...skipping 14 matching lines...) Expand all Loading... |
318 } else { | 389 } else { |
319 // TODO(johnniwinther): Convert `node.location` to a [SourceSpan]. | 390 // TODO(johnniwinther): Convert `node.location` to a [SourceSpan]. |
320 throw new SpannableAssertionFailure( | 391 throw new SpannableAssertionFailure( |
321 NO_LOCATION_SPANNABLE, "Unexpected constructor node: ${node}."); | 392 NO_LOCATION_SPANNABLE, "Unexpected constructor node: ${node}."); |
322 } | 393 } |
323 _memberList.add(new _ConstructorData(node, functionNode)); | 394 _memberList.add(new _ConstructorData(node, functionNode)); |
324 return constructor; | 395 return constructor; |
325 }); | 396 }); |
326 } | 397 } |
327 | 398 |
| 399 ConstructorEntity getSuperConstructor( |
| 400 ir.Constructor sourceNode, ir.Member targetNode) { |
| 401 KConstructor source = getConstructor(sourceNode); |
| 402 KClass sourceClass = source.enclosingClass; |
| 403 KConstructor target = getConstructor(targetNode); |
| 404 KClass targetClass = target.enclosingClass; |
| 405 KClass superClass = _getSuperType(sourceClass)?.element; |
| 406 if (superClass == targetClass) { |
| 407 return target; |
| 408 } |
| 409 _KClassEnv env = _classEnvs[superClass.classIndex]; |
| 410 ir.Member member = env.lookupConstructor(target.name); |
| 411 if (member != null) { |
| 412 return getConstructor(member); |
| 413 } |
| 414 throw new SpannableAssertionFailure( |
| 415 source, "Super constructor for $source not found."); |
| 416 } |
| 417 |
| 418 @override |
| 419 FunctionEntity getMethod(ir.Procedure node) => _getMethod(node); |
| 420 |
328 KFunction _getMethod(ir.Procedure node) { | 421 KFunction _getMethod(ir.Procedure node) { |
329 return _methodMap.putIfAbsent(node, () { | 422 return _methodMap.putIfAbsent(node, () { |
330 int memberIndex = _memberList.length; | 423 int memberIndex = _memberList.length; |
331 KLibrary library; | 424 KLibrary library; |
332 KClass enclosingClass; | 425 KClass enclosingClass; |
333 if (node.enclosingClass != null) { | 426 if (node.enclosingClass != null) { |
334 enclosingClass = _getClass(node.enclosingClass); | 427 enclosingClass = _getClass(node.enclosingClass); |
335 library = enclosingClass.library; | 428 library = enclosingClass.library; |
336 } else { | 429 } else { |
337 library = _getLibrary(node.enclosingLibrary); | 430 library = _getLibrary(node.enclosingLibrary); |
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
384 isStatic: isStatic, | 477 isStatic: isStatic, |
385 isExternal: isExternal, | 478 isExternal: isExternal, |
386 isAbstract: isAbstract); | 479 isAbstract: isAbstract); |
387 break; | 480 break; |
388 } | 481 } |
389 _memberList.add(new _FunctionData(node, node.function)); | 482 _memberList.add(new _FunctionData(node, node.function)); |
390 return function; | 483 return function; |
391 }); | 484 }); |
392 } | 485 } |
393 | 486 |
394 MemberEntity getSuperMember(ir.Member context, ir.Name name, ir.Member target, | 487 @override |
395 {bool setter: false}) { | 488 FieldEntity getField(ir.Field node) => _getField(node); |
396 if (target != null) { | |
397 return getMember(target); | |
398 } | |
399 KClass cls = getMember(context).enclosingClass; | |
400 KClass superclass = _getSuperType(cls)?.element; | |
401 while (superclass != null) { | |
402 _KClassEnv env = _classEnvs[superclass.classIndex]; | |
403 ir.Member superMember = env.lookupMember(name.name, setter: setter); | |
404 if (superMember != null) { | |
405 return getMember(superMember); | |
406 } | |
407 superclass = _getSuperType(superclass)?.element; | |
408 } | |
409 throw new SpannableAssertionFailure( | |
410 cls, "No super method member found for ${name} in $cls."); | |
411 } | |
412 | |
413 /// Returns the kernel [ir.Procedure] node for the [method]. | |
414 ir.Procedure _lookupProcedure(KFunction method) { | |
415 return _memberList[method.memberIndex].node; | |
416 } | |
417 | 489 |
418 KField _getField(ir.Field node) { | 490 KField _getField(ir.Field node) { |
419 return _fieldMap.putIfAbsent(node, () { | 491 return _fieldMap.putIfAbsent(node, () { |
420 int memberIndex = _memberList.length; | 492 int memberIndex = _memberList.length; |
421 KLibrary library; | 493 KLibrary library; |
422 KClass enclosingClass; | 494 KClass enclosingClass; |
423 if (node.enclosingClass != null) { | 495 if (node.enclosingClass != null) { |
424 enclosingClass = _getClass(node.enclosingClass); | 496 enclosingClass = _getClass(node.enclosingClass); |
425 library = enclosingClass.library; | 497 library = enclosingClass.library; |
426 } else { | 498 } else { |
427 library = _getLibrary(node.enclosingLibrary); | 499 library = _getLibrary(node.enclosingLibrary); |
428 } | 500 } |
429 Name name = getName(node.name); | 501 Name name = getName(node.name); |
430 bool isStatic = node.isStatic; | 502 bool isStatic = node.isStatic; |
431 _memberList.add(new _FieldData(node)); | 503 _memberList.add(new _FieldData(node)); |
432 return new KField(memberIndex, library, enclosingClass, name, | 504 return new KField(memberIndex, library, enclosingClass, name, |
433 isStatic: isStatic, | 505 isStatic: isStatic, |
434 isAssignable: node.isMutable, | 506 isAssignable: node.isMutable, |
435 isConst: node.isConst); | 507 isConst: node.isConst); |
436 }); | 508 }); |
437 } | 509 } |
438 | 510 |
| 511 ParameterStructure _getParameterStructure(ir.FunctionNode node) { |
| 512 // TODO(johnniwinther): Cache the computed function type. |
| 513 int requiredParameters = node.requiredParameterCount; |
| 514 int positionalParameters = node.positionalParameters.length; |
| 515 List<String> namedParameters = |
| 516 node.namedParameters.map((p) => p.name).toList()..sort(); |
| 517 return new ParameterStructure( |
| 518 requiredParameters, positionalParameters, namedParameters); |
| 519 } |
| 520 |
| 521 @override |
| 522 Local getLocalFunction(ir.TreeNode node) => _getLocal(node); |
| 523 |
439 KLocalFunction _getLocal(ir.TreeNode node) { | 524 KLocalFunction _getLocal(ir.TreeNode node) { |
440 return _localFunctionMap.putIfAbsent(node, () { | 525 return _localFunctionMap.putIfAbsent(node, () { |
441 MemberEntity memberContext; | 526 MemberEntity memberContext; |
442 Entity executableContext; | 527 Entity executableContext; |
443 ir.TreeNode parent = node.parent; | 528 ir.TreeNode parent = node.parent; |
444 while (parent != null) { | 529 while (parent != null) { |
445 if (parent is ir.Member) { | 530 if (parent is ir.Member) { |
446 executableContext = memberContext = getMember(parent); | 531 executableContext = memberContext = getMember(parent); |
447 break; | 532 break; |
448 } | 533 } |
(...skipping 15 matching lines...) Expand all Loading... |
464 functionType = getFunctionType(node.function); | 549 functionType = getFunctionType(node.function); |
465 } | 550 } |
466 return new KLocalFunction( | 551 return new KLocalFunction( |
467 name, memberContext, executableContext, functionType); | 552 name, memberContext, executableContext, functionType); |
468 }); | 553 }); |
469 } | 554 } |
470 | 555 |
471 @override | 556 @override |
472 DartType getDartType(ir.DartType type) => _typeConverter.convert(type); | 557 DartType getDartType(ir.DartType type) => _typeConverter.convert(type); |
473 | 558 |
474 @override | |
475 InterfaceType createInterfaceType( | |
476 ir.Class cls, List<ir.DartType> typeArguments) { | |
477 return new InterfaceType(getClass(cls), getDartTypes(typeArguments)); | |
478 } | |
479 | |
480 @override | |
481 InterfaceType getInterfaceType(ir.InterfaceType type) => | |
482 _typeConverter.convert(type); | |
483 | |
484 @override | |
485 List<DartType> getDartTypes(List<ir.DartType> types) { | 559 List<DartType> getDartTypes(List<ir.DartType> types) { |
486 // TODO(johnniwinther): Add the type argument to the list literal when we | 560 // TODO(johnniwinther): Add the type argument to the list literal when we |
487 // no longer use resolution types. | 561 // no longer use resolution types. |
488 List<DartType> list = /*<DartType>*/ []; | 562 List<DartType> list = /*<DartType>*/ []; |
489 types.forEach((ir.DartType type) { | 563 types.forEach((ir.DartType type) { |
490 list.add(getDartType(type)); | 564 list.add(getDartType(type)); |
491 }); | 565 }); |
492 return list; | 566 return list; |
493 } | 567 } |
494 | 568 |
495 void _ensureThisAndRawType(KClass cls, _KClassEnv env) { | 569 @override |
496 if (env.thisType == null) { | 570 InterfaceType getInterfaceType(ir.InterfaceType type) => |
497 ir.Class node = env.cls; | 571 _typeConverter.convert(type); |
498 // TODO(johnniwinther): Add the type argument to the list literal when we | 572 |
499 // no longer use resolution types. | 573 @override |
500 if (node.typeParameters.isEmpty) { | 574 FunctionType getFunctionType(ir.FunctionNode node) { |
501 env.thisType = | 575 DartType returnType = getDartType(node.returnType); |
502 env.rawType = new InterfaceType(cls, const/*<DartType>*/ []); | 576 List<DartType> parameterTypes = /*<DartType>*/ []; |
| 577 List<DartType> optionalParameterTypes = /*<DartType>*/ []; |
| 578 for (ir.VariableDeclaration variable in node.positionalParameters) { |
| 579 if (parameterTypes.length == node.requiredParameterCount) { |
| 580 optionalParameterTypes.add(getDartType(variable.type)); |
503 } else { | 581 } else { |
504 env.thisType = new InterfaceType( | 582 parameterTypes.add(getDartType(variable.type)); |
505 cls, | |
506 new List/*<DartType>*/ .generate(node.typeParameters.length, | |
507 (int index) { | |
508 return new TypeVariableType( | |
509 _getTypeVariable(node.typeParameters[index])); | |
510 })); | |
511 env.rawType = new InterfaceType( | |
512 cls, | |
513 new List/*<DartType>*/ .filled( | |
514 node.typeParameters.length, const DynamicType())); | |
515 } | 583 } |
516 } | 584 } |
| 585 List<String> namedParameters = <String>[]; |
| 586 List<DartType> namedParameterTypes = /*<DartType>*/ []; |
| 587 List<ir.VariableDeclaration> sortedNamedParameters = |
| 588 node.namedParameters.toList()..sort((a, b) => a.name.compareTo(b.name)); |
| 589 for (ir.VariableDeclaration variable in sortedNamedParameters) { |
| 590 namedParameters.add(variable.name); |
| 591 namedParameterTypes.add(getDartType(variable.type)); |
| 592 } |
| 593 return new FunctionType(returnType, parameterTypes, optionalParameterTypes, |
| 594 namedParameters, namedParameterTypes); |
| 595 } |
| 596 |
| 597 @override |
| 598 ConstantValue computeConstantValue(ConstantExpression constant, |
| 599 {bool requireConstant: true}) { |
| 600 return _constantEnvironment.getConstantValue(constant); |
| 601 } |
| 602 |
| 603 DartType _substByContext(DartType type, InterfaceType context) { |
| 604 return type.subst( |
| 605 context.typeArguments, _getThisType(context.element).typeArguments); |
517 } | 606 } |
518 | 607 |
519 InterfaceType _getThisType(KClass cls) { | 608 InterfaceType _getThisType(KClass cls) { |
520 _KClassEnv env = _classEnvs[cls.classIndex]; | 609 _KClassEnv env = _classEnvs[cls.classIndex]; |
521 _ensureThisAndRawType(cls, env); | 610 _ensureThisAndRawType(cls, env); |
522 return env.thisType; | 611 return env.thisType; |
523 } | 612 } |
524 | 613 |
525 InterfaceType _getRawType(KClass cls) { | 614 InterfaceType _getRawType(KClass cls) { |
526 _KClassEnv env = _classEnvs[cls.classIndex]; | 615 _KClassEnv env = _classEnvs[cls.classIndex]; |
527 _ensureThisAndRawType(cls, env); | 616 _ensureThisAndRawType(cls, env); |
528 return env.rawType; | 617 return env.rawType; |
529 } | 618 } |
530 | 619 |
531 InterfaceType _asInstanceOf(InterfaceType type, KClass cls) { | 620 FunctionType _getFunctionType(KFunction function) { |
532 OrderedTypeSet orderedTypeSet = _getOrderedTypeSet(type.element); | 621 _FunctionData data = _memberList[function.memberIndex]; |
533 InterfaceType supertype = | 622 return data.getFunctionType(this); |
534 orderedTypeSet.asInstanceOf(cls, _getHierarchyDepth(cls)); | |
535 if (supertype != null) { | |
536 supertype = _substByContext(supertype, type); | |
537 } | |
538 return supertype; | |
539 } | |
540 | |
541 void _ensureSupertypes(KClass cls, _KClassEnv env) { | |
542 if (env.orderedTypeSet == null) { | |
543 _ensureThisAndRawType(cls, env); | |
544 | |
545 ir.Class node = env.cls; | |
546 | |
547 if (node.supertype == null) { | |
548 env.orderedTypeSet = new OrderedTypeSet.singleton(env.thisType); | |
549 env.isMixinApplication = false; | |
550 env.interfaces = const <InterfaceType>[]; | |
551 } else { | |
552 InterfaceType processSupertype(ir.Supertype node) { | |
553 InterfaceType type = _typeConverter.visitSupertype(node); | |
554 KClass superclass = type.element; | |
555 _KClassEnv env = _classEnvs[superclass.classIndex]; | |
556 _ensureSupertypes(superclass, env); | |
557 return type; | |
558 } | |
559 | |
560 env.supertype = processSupertype(node.supertype); | |
561 LinkBuilder<InterfaceType> linkBuilder = | |
562 new LinkBuilder<InterfaceType>(); | |
563 if (node.mixedInType != null) { | |
564 env.isMixinApplication = true; | |
565 linkBuilder | |
566 .addLast(env.mixedInType = processSupertype(node.mixedInType)); | |
567 } else { | |
568 env.isMixinApplication = false; | |
569 } | |
570 node.implementedTypes.forEach((ir.Supertype supertype) { | |
571 linkBuilder.addLast(processSupertype(supertype)); | |
572 }); | |
573 Link<InterfaceType> interfaces = linkBuilder.toLink(); | |
574 OrderedTypeSetBuilder setBuilder = | |
575 new _KernelOrderedTypeSetBuilder(this, cls); | |
576 env.orderedTypeSet = | |
577 setBuilder.createOrderedTypeSet(env.supertype, interfaces); | |
578 env.interfaces = new List<InterfaceType>.from(interfaces.toList()); | |
579 } | |
580 } | |
581 } | |
582 | |
583 OrderedTypeSet _getOrderedTypeSet(KClass cls) { | |
584 _KClassEnv env = _classEnvs[cls.classIndex]; | |
585 _ensureSupertypes(cls, env); | |
586 return env.orderedTypeSet; | |
587 } | |
588 | |
589 int _getHierarchyDepth(KClass cls) { | |
590 _KClassEnv env = _classEnvs[cls.classIndex]; | |
591 _ensureSupertypes(cls, env); | |
592 return env.orderedTypeSet.maxDepth; | |
593 } | 623 } |
594 | 624 |
595 ClassEntity _getAppliedMixin(KClass cls) { | 625 ClassEntity _getAppliedMixin(KClass cls) { |
596 _KClassEnv env = _classEnvs[cls.classIndex]; | 626 _KClassEnv env = _classEnvs[cls.classIndex]; |
597 _ensureSupertypes(cls, env); | 627 _ensureSupertypes(cls, env); |
598 return env.mixedInType?.element; | 628 return env.mixedInType?.element; |
599 } | 629 } |
600 | 630 |
601 DartType _substByContext(DartType type, InterfaceType context) { | |
602 return type.subst( | |
603 context.typeArguments, _getThisType(context.element).typeArguments); | |
604 } | |
605 | |
606 InterfaceType _getSuperType(KClass cls) { | |
607 _KClassEnv env = _classEnvs[cls.classIndex]; | |
608 _ensureSupertypes(cls, env); | |
609 return env.supertype; | |
610 } | |
611 | |
612 bool _isMixinApplication(KClass cls) { | 631 bool _isMixinApplication(KClass cls) { |
613 _KClassEnv env = _classEnvs[cls.classIndex]; | 632 _KClassEnv env = _classEnvs[cls.classIndex]; |
614 _ensureSupertypes(cls, env); | 633 _ensureSupertypes(cls, env); |
615 return env.isMixinApplication; | 634 return env.isMixinApplication; |
616 } | 635 } |
617 | 636 |
618 bool _isUnnamedMixinApplication(KClass cls) { | 637 bool _isUnnamedMixinApplication(KClass cls) { |
619 _KClassEnv env = _classEnvs[cls.classIndex]; | 638 _KClassEnv env = _classEnvs[cls.classIndex]; |
620 _ensureSupertypes(cls, env); | 639 _ensureSupertypes(cls, env); |
621 return env.isUnnamedMixinApplication; | 640 return env.isUnnamedMixinApplication; |
622 } | 641 } |
623 | 642 |
624 Iterable<InterfaceType> _getInterfaces(KClass cls) { | |
625 _KClassEnv env = _classEnvs[cls.classIndex]; | |
626 _ensureSupertypes(cls, env); | |
627 return env.interfaces; | |
628 } | |
629 | |
630 void _forEachSupertype(KClass cls, void f(InterfaceType supertype)) { | 643 void _forEachSupertype(KClass cls, void f(InterfaceType supertype)) { |
631 _KClassEnv env = _classEnvs[cls.classIndex]; | 644 _KClassEnv env = _classEnvs[cls.classIndex]; |
632 _ensureSupertypes(cls, env); | 645 _ensureSupertypes(cls, env); |
633 env.orderedTypeSet.supertypes.forEach(f); | 646 env.orderedTypeSet.supertypes.forEach(f); |
634 } | 647 } |
635 | 648 |
636 void _forEachMixin(KClass cls, void f(ClassEntity mixin)) { | 649 void _forEachMixin(KClass cls, void f(ClassEntity mixin)) { |
637 while (cls != null) { | 650 while (cls != null) { |
638 _KClassEnv env = _classEnvs[cls.classIndex]; | 651 _KClassEnv env = _classEnvs[cls.classIndex]; |
639 _ensureSupertypes(cls, env); | 652 _ensureSupertypes(cls, env); |
(...skipping 16 matching lines...) Expand all Loading... |
656 _KClassEnv env = _classEnvs[cls.classIndex]; | 669 _KClassEnv env = _classEnvs[cls.classIndex]; |
657 env.forEachMember((ir.Member member) { | 670 env.forEachMember((ir.Member member) { |
658 f(cls, getMember(member)); | 671 f(cls, getMember(member)); |
659 }); | 672 }); |
660 _ensureSupertypes(cls, env); | 673 _ensureSupertypes(cls, env); |
661 if (env.supertype != null) { | 674 if (env.supertype != null) { |
662 _forEachClassMember(env.supertype.element, f); | 675 _forEachClassMember(env.supertype.element, f); |
663 } | 676 } |
664 } | 677 } |
665 | 678 |
666 @override | 679 ConstantConstructor _getConstructorConstant(KConstructor constructor) { |
667 FunctionType getFunctionType(ir.FunctionNode node) { | 680 _ConstructorData data = _memberList[constructor.memberIndex]; |
668 DartType returnType = getDartType(node.returnType); | 681 return data.getConstructorConstant(this, constructor); |
669 List<DartType> parameterTypes = /*<DartType>*/ []; | |
670 List<DartType> optionalParameterTypes = /*<DartType>*/ []; | |
671 for (ir.VariableDeclaration variable in node.positionalParameters) { | |
672 if (parameterTypes.length == node.requiredParameterCount) { | |
673 optionalParameterTypes.add(getDartType(variable.type)); | |
674 } else { | |
675 parameterTypes.add(getDartType(variable.type)); | |
676 } | |
677 } | |
678 List<String> namedParameters = <String>[]; | |
679 List<DartType> namedParameterTypes = /*<DartType>*/ []; | |
680 List<ir.VariableDeclaration> sortedNamedParameters = | |
681 node.namedParameters.toList()..sort((a, b) => a.name.compareTo(b.name)); | |
682 for (ir.VariableDeclaration variable in sortedNamedParameters) { | |
683 namedParameters.add(variable.name); | |
684 namedParameterTypes.add(getDartType(variable.type)); | |
685 } | |
686 return new FunctionType(returnType, parameterTypes, optionalParameterTypes, | |
687 namedParameters, namedParameterTypes); | |
688 } | 682 } |
689 | 683 |
690 LibraryEntity getLibrary(ir.Library node) => _getLibrary(node); | 684 ConstantExpression _getFieldConstant(KField field) { |
| 685 _FieldData data = _memberList[field.memberIndex]; |
| 686 return data.getFieldConstant(this, field); |
| 687 } |
| 688 } |
| 689 |
| 690 class KernelToElementMapForImpactImpl extends KernelToElementMapBase |
| 691 with KernelToElementMapForImpactMixin { |
| 692 native.BehaviorBuilder _nativeBehaviorBuilder; |
| 693 |
| 694 KernelToElementMapForImpactImpl( |
| 695 DiagnosticReporter reporter, Environment environment) |
| 696 : super(reporter, environment) { |
| 697 _nativeBehaviorBuilder = new KernelBehaviorBuilder(_commonElements); |
| 698 } |
| 699 |
| 700 @override |
| 701 native.BehaviorBuilder get nativeBehaviorBuilder => _nativeBehaviorBuilder; |
| 702 } |
| 703 |
| 704 /// Element builder used for creating elements and types corresponding to Kernel |
| 705 /// IR nodes. |
| 706 class KernelToElementMapImpl extends KernelToElementMapForImpactImpl |
| 707 with KernelToElementMapForBuildingMixin |
| 708 implements KernelToWorldBuilder { |
| 709 _KernelDartTypes _types; |
| 710 |
| 711 KernelToElementMapImpl(DiagnosticReporter reporter, Environment environment) |
| 712 : super(reporter, environment) { |
| 713 _types = new _KernelDartTypes(this); |
| 714 } |
| 715 |
| 716 /// Adds libraries in [program] to the set of libraries. |
| 717 /// |
| 718 /// The main method of the first program is used as the main method for the |
| 719 /// compilation. |
| 720 void addProgram(ir.Program program) { |
| 721 _env.addProgram(program); |
| 722 } |
| 723 |
| 724 ConstantEnvironment get constantEnvironment => _constantEnvironment; |
| 725 |
| 726 DartTypes get types => _types; |
| 727 |
| 728 @override |
| 729 ConstantValue getFieldConstantValue(ir.Field field) { |
| 730 // TODO(johnniwinther): Cache the result in [_FieldData]. |
| 731 return getConstantValue(field.initializer, |
| 732 requireConstant: field.isConst, implicitNull: !field.isConst); |
| 733 } |
| 734 |
| 735 Iterable<ConstantValue> _getClassMetadata(KClass cls) { |
| 736 return _classEnvs[cls.classIndex].getMetadata(this); |
| 737 } |
| 738 |
| 739 /// Returns the kernel [ir.Procedure] node for the [method]. |
| 740 ir.Procedure _lookupProcedure(KFunction method) { |
| 741 return _memberList[method.memberIndex].node; |
| 742 } |
| 743 |
| 744 InterfaceType _asInstanceOf(InterfaceType type, KClass cls) { |
| 745 OrderedTypeSet orderedTypeSet = _getOrderedTypeSet(type.element); |
| 746 InterfaceType supertype = |
| 747 orderedTypeSet.asInstanceOf(cls, _getHierarchyDepth(cls)); |
| 748 if (supertype != null) { |
| 749 supertype = _substByContext(supertype, type); |
| 750 } |
| 751 return supertype; |
| 752 } |
| 753 |
| 754 OrderedTypeSet _getOrderedTypeSet(KClass cls) { |
| 755 _KClassEnv env = _classEnvs[cls.classIndex]; |
| 756 _ensureSupertypes(cls, env); |
| 757 return env.orderedTypeSet; |
| 758 } |
| 759 |
| 760 int _getHierarchyDepth(KClass cls) { |
| 761 _KClassEnv env = _classEnvs[cls.classIndex]; |
| 762 _ensureSupertypes(cls, env); |
| 763 return env.orderedTypeSet.maxDepth; |
| 764 } |
| 765 |
| 766 Iterable<InterfaceType> _getInterfaces(KClass cls) { |
| 767 _KClassEnv env = _classEnvs[cls.classIndex]; |
| 768 _ensureSupertypes(cls, env); |
| 769 return env.interfaces; |
| 770 } |
691 | 771 |
692 ir.Library getKernelLibrary(KLibrary entity) => | 772 ir.Library getKernelLibrary(KLibrary entity) => |
693 _libraryEnvs[entity.libraryIndex].library; | 773 _libraryEnvs[entity.libraryIndex].library; |
694 | 774 |
695 ir.Class getKernelClass(KClass entity) => _classEnvs[entity.classIndex].cls; | 775 ir.Class getKernelClass(KClass entity) => _classEnvs[entity.classIndex].cls; |
696 | 776 |
697 @override | |
698 Local getLocalFunction(ir.TreeNode node) => _getLocal(node); | |
699 | |
700 @override | |
701 ClassEntity getClass(ir.Class node) => _getClass(node); | |
702 | |
703 @override | |
704 FieldEntity getField(ir.Field node) => _getField(node); | |
705 | |
706 bool hasConstantFieldInitializer(covariant KField field) { | 777 bool hasConstantFieldInitializer(covariant KField field) { |
707 _FieldData data = _memberList[field.memberIndex]; | 778 _FieldData data = _memberList[field.memberIndex]; |
708 return getFieldConstantValue(data.node) != null; | 779 return getFieldConstantValue(data.node) != null; |
709 } | 780 } |
710 | 781 |
711 ConstantValue getConstantFieldInitializer(covariant KField field) { | 782 ConstantValue getConstantFieldInitializer(covariant KField field) { |
712 _FieldData data = _memberList[field.memberIndex]; | 783 _FieldData data = _memberList[field.memberIndex]; |
713 ConstantValue value = getFieldConstantValue(data.node); | 784 ConstantValue value = getFieldConstantValue(data.node); |
714 assert(value != null, | 785 assert(value != null, |
715 failedAt(field, "Field $field doesn't have a constant initial value.")); | 786 failedAt(field, "Field $field doesn't have a constant initial value.")); |
716 return value; | 787 return value; |
717 } | 788 } |
718 | 789 |
719 TypeVariableEntity getTypeVariable(ir.TypeParameter node) => | |
720 _getTypeVariable(node); | |
721 | |
722 @override | |
723 FunctionEntity getMethod(ir.Procedure node) => _getMethod(node); | |
724 | |
725 void forEachParameter(covariant KFunction function, | 790 void forEachParameter(covariant KFunction function, |
726 void f(DartType type, String name, ConstantValue defaultValue)) { | 791 void f(DartType type, String name, ConstantValue defaultValue)) { |
727 _FunctionData data = _memberList[function.memberIndex]; | 792 _FunctionData data = _memberList[function.memberIndex]; |
728 data.forEachParameter(this, f); | 793 data.forEachParameter(this, f); |
729 } | 794 } |
730 | 795 |
731 @override | |
732 MemberEntity getMember(ir.Member node) { | |
733 if (node is ir.Field) { | |
734 return _getField(node); | |
735 } else if (node is ir.Constructor) { | |
736 return _getConstructor(node); | |
737 } else if (node is ir.Procedure) { | |
738 if (node.kind == ir.ProcedureKind.Factory) { | |
739 return _getConstructor(node); | |
740 } else { | |
741 return _getMethod(node); | |
742 } | |
743 } | |
744 throw new UnsupportedError("Unexpected member: $node"); | |
745 } | |
746 | |
747 @override | |
748 ConstructorEntity getConstructor(ir.Member node) => _getConstructor(node); | |
749 | |
750 @override | |
751 ConstructorEntity getSuperConstructor( | |
752 ir.Constructor sourceNode, ir.Member targetNode) { | |
753 KConstructor source = getConstructor(sourceNode); | |
754 KClass sourceClass = source.enclosingClass; | |
755 KConstructor target = getConstructor(targetNode); | |
756 KClass targetClass = target.enclosingClass; | |
757 KClass superClass = _getSuperType(sourceClass)?.element; | |
758 if (superClass == targetClass) { | |
759 return target; | |
760 } | |
761 _KClassEnv env = _classEnvs[superClass.classIndex]; | |
762 ir.Member member = env.lookupConstructor(target.name); | |
763 if (member != null) { | |
764 return getConstructor(member); | |
765 } | |
766 throw new SpannableAssertionFailure( | |
767 source, "Super constructor for $source not found."); | |
768 } | |
769 | |
770 ConstantConstructor _getConstructorConstant(KConstructor constructor) { | |
771 _ConstructorData data = _memberList[constructor.memberIndex]; | |
772 return data.getConstructorConstant(this, constructor); | |
773 } | |
774 | |
775 ConstantExpression _getFieldConstant(KField field) { | |
776 _FieldData data = _memberList[field.memberIndex]; | |
777 return data.getFieldConstant(this, field); | |
778 } | |
779 | |
780 FunctionType _getFunctionType(KFunction function) { | |
781 _FunctionData data = _memberList[function.memberIndex]; | |
782 return data.getFunctionType(this); | |
783 } | |
784 | |
785 ResolutionImpact computeWorldImpact(KMember member) { | 796 ResolutionImpact computeWorldImpact(KMember member) { |
786 return _memberList[member.memberIndex].getWorldImpact(this); | 797 return _memberList[member.memberIndex].getWorldImpact(this); |
787 } | 798 } |
788 | 799 |
789 @override | 800 @override |
790 Spannable getSpannable(MemberEntity member, ir.Node node) { | 801 Spannable getSpannable(MemberEntity member, ir.Node node) { |
791 return member; | 802 return member; |
792 } | 803 } |
793 | 804 |
794 @override | 805 @override |
(...skipping 388 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1183 field, | 1194 field, |
1184 "Unexpected field $field in " | 1195 "Unexpected field $field in " |
1185 "KernelWorldBuilder._getConstructorConstant"); | 1196 "KernelWorldBuilder._getConstructorConstant"); |
1186 } | 1197 } |
1187 } | 1198 } |
1188 return _constant; | 1199 return _constant; |
1189 } | 1200 } |
1190 } | 1201 } |
1191 | 1202 |
1192 class KernelElementEnvironment implements ElementEnvironment { | 1203 class KernelElementEnvironment implements ElementEnvironment { |
1193 final KernelToElementMapImpl elementMap; | 1204 final KernelToElementMapBase elementMap; |
1194 | 1205 |
1195 KernelElementEnvironment(this.elementMap); | 1206 KernelElementEnvironment(this.elementMap); |
1196 | 1207 |
1197 @override | 1208 @override |
1198 DartType get dynamicType => const DynamicType(); | 1209 DartType get dynamicType => const DynamicType(); |
1199 | 1210 |
1200 @override | 1211 @override |
1201 LibraryEntity get mainLibrary => elementMap._mainLibrary; | 1212 LibraryEntity get mainLibrary => elementMap._mainLibrary; |
1202 | 1213 |
1203 @override | 1214 @override |
(...skipping 178 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1382 | 1393 |
1383 @override | 1394 @override |
1384 Iterable<ConstantValue> getMemberMetadata(covariant KMember member) { | 1395 Iterable<ConstantValue> getMemberMetadata(covariant KMember member) { |
1385 _MemberData memberData = elementMap._memberList[member.memberIndex]; | 1396 _MemberData memberData = elementMap._memberList[member.memberIndex]; |
1386 return memberData.getMetadata(elementMap); | 1397 return memberData.getMetadata(elementMap); |
1387 } | 1398 } |
1388 } | 1399 } |
1389 | 1400 |
1390 /// Visitor that converts kernel dart types into [DartType]. | 1401 /// Visitor that converts kernel dart types into [DartType]. |
1391 class DartTypeConverter extends ir.DartTypeVisitor<DartType> { | 1402 class DartTypeConverter extends ir.DartTypeVisitor<DartType> { |
1392 final KernelToElementMapImpl elementAdapter; | 1403 final KernelToElementMapBase elementMap; |
1393 bool topLevel = true; | 1404 bool topLevel = true; |
1394 | 1405 |
1395 DartTypeConverter(this.elementAdapter); | 1406 DartTypeConverter(this.elementMap); |
1396 | 1407 |
1397 DartType convert(ir.DartType type) { | 1408 DartType convert(ir.DartType type) { |
1398 topLevel = true; | 1409 topLevel = true; |
1399 return type.accept(this); | 1410 return type.accept(this); |
1400 } | 1411 } |
1401 | 1412 |
1402 /// Visit a inner type. | 1413 /// Visit a inner type. |
1403 DartType visitType(ir.DartType type) { | 1414 DartType visitType(ir.DartType type) { |
1404 topLevel = false; | 1415 topLevel = false; |
1405 return type.accept(this); | 1416 return type.accept(this); |
1406 } | 1417 } |
1407 | 1418 |
1408 InterfaceType visitSupertype(ir.Supertype node) { | 1419 InterfaceType visitSupertype(ir.Supertype node) { |
1409 ClassEntity cls = elementAdapter.getClass(node.classNode); | 1420 ClassEntity cls = elementMap.getClass(node.classNode); |
1410 return new InterfaceType(cls, visitTypes(node.typeArguments)); | 1421 return new InterfaceType(cls, visitTypes(node.typeArguments)); |
1411 } | 1422 } |
1412 | 1423 |
1413 List<DartType> visitTypes(List<ir.DartType> types) { | 1424 List<DartType> visitTypes(List<ir.DartType> types) { |
1414 topLevel = false; | 1425 topLevel = false; |
1415 return new List.generate( | 1426 return new List.generate( |
1416 types.length, (int index) => types[index].accept(this)); | 1427 types.length, (int index) => types[index].accept(this)); |
1417 } | 1428 } |
1418 | 1429 |
1419 @override | 1430 @override |
1420 DartType visitTypeParameterType(ir.TypeParameterType node) { | 1431 DartType visitTypeParameterType(ir.TypeParameterType node) { |
1421 return new TypeVariableType(elementAdapter.getTypeVariable(node.parameter)); | 1432 return new TypeVariableType(elementMap.getTypeVariable(node.parameter)); |
1422 } | 1433 } |
1423 | 1434 |
1424 @override | 1435 @override |
1425 DartType visitFunctionType(ir.FunctionType node) { | 1436 DartType visitFunctionType(ir.FunctionType node) { |
1426 return new FunctionType( | 1437 return new FunctionType( |
1427 visitType(node.returnType), | 1438 visitType(node.returnType), |
1428 visitTypes(node.positionalParameters | 1439 visitTypes(node.positionalParameters |
1429 .take(node.requiredParameterCount) | 1440 .take(node.requiredParameterCount) |
1430 .toList()), | 1441 .toList()), |
1431 visitTypes(node.positionalParameters | 1442 visitTypes(node.positionalParameters |
1432 .skip(node.requiredParameterCount) | 1443 .skip(node.requiredParameterCount) |
1433 .toList()), | 1444 .toList()), |
1434 node.namedParameters.map((n) => n.name).toList(), | 1445 node.namedParameters.map((n) => n.name).toList(), |
1435 node.namedParameters.map((n) => visitType(n.type)).toList()); | 1446 node.namedParameters.map((n) => visitType(n.type)).toList()); |
1436 } | 1447 } |
1437 | 1448 |
1438 @override | 1449 @override |
1439 DartType visitInterfaceType(ir.InterfaceType node) { | 1450 DartType visitInterfaceType(ir.InterfaceType node) { |
1440 ClassEntity cls = elementAdapter.getClass(node.classNode); | 1451 ClassEntity cls = elementMap.getClass(node.classNode); |
1441 return new InterfaceType(cls, visitTypes(node.typeArguments)); | 1452 return new InterfaceType(cls, visitTypes(node.typeArguments)); |
1442 } | 1453 } |
1443 | 1454 |
1444 @override | 1455 @override |
1445 DartType visitVoidType(ir.VoidType node) { | 1456 DartType visitVoidType(ir.VoidType node) { |
1446 return const VoidType(); | 1457 return const VoidType(); |
1447 } | 1458 } |
1448 | 1459 |
1449 @override | 1460 @override |
1450 DartType visitDynamicType(ir.DynamicType node) { | 1461 DartType visitDynamicType(ir.DynamicType node) { |
(...skipping 27 matching lines...) Expand all Loading... |
1478 | 1489 |
1479 NativeBasicData get nativeBasicData { | 1490 NativeBasicData get nativeBasicData { |
1480 throw new UnimplementedError( | 1491 throw new UnimplementedError( |
1481 "KernelNativeBehaviorComputer.nativeBasicData"); | 1492 "KernelNativeBehaviorComputer.nativeBasicData"); |
1482 } | 1493 } |
1483 } | 1494 } |
1484 | 1495 |
1485 /// Constant environment mapping [ConstantExpression]s to [ConstantValue]s using | 1496 /// Constant environment mapping [ConstantExpression]s to [ConstantValue]s using |
1486 /// [_EvaluationEnvironment] for the evaluation. | 1497 /// [_EvaluationEnvironment] for the evaluation. |
1487 class KernelConstantEnvironment implements ConstantEnvironment { | 1498 class KernelConstantEnvironment implements ConstantEnvironment { |
1488 KernelToElementMapForBuilding _worldBuilder; | 1499 final KernelToElementMapBase _elementMap; |
| 1500 final Environment _environment; |
| 1501 |
1489 Map<ConstantExpression, ConstantValue> _valueMap = | 1502 Map<ConstantExpression, ConstantValue> _valueMap = |
1490 <ConstantExpression, ConstantValue>{}; | 1503 <ConstantExpression, ConstantValue>{}; |
1491 | 1504 |
1492 KernelConstantEnvironment(this._worldBuilder); | 1505 KernelConstantEnvironment(this._elementMap, this._environment); |
1493 | 1506 |
1494 @override | 1507 @override |
1495 ConstantSystem get constantSystem => const JavaScriptConstantSystem(); | 1508 ConstantSystem get constantSystem => const JavaScriptConstantSystem(); |
1496 | 1509 |
1497 @override | 1510 @override |
1498 ConstantValue getConstantValueForVariable(VariableElement element) { | 1511 ConstantValue getConstantValueForVariable(VariableElement element) { |
1499 throw new UnimplementedError( | 1512 throw new UnimplementedError( |
1500 "KernelConstantEnvironment.getConstantValueForVariable"); | 1513 "KernelConstantEnvironment.getConstantValueForVariable"); |
1501 } | 1514 } |
1502 | 1515 |
1503 @override | 1516 @override |
1504 ConstantValue getConstantValue(ConstantExpression expression) { | 1517 ConstantValue getConstantValue(ConstantExpression expression) { |
1505 return _valueMap.putIfAbsent(expression, () { | 1518 return _valueMap.putIfAbsent(expression, () { |
1506 return expression.evaluate( | 1519 return expression.evaluate( |
1507 new _EvaluationEnvironment(_worldBuilder), constantSystem); | 1520 new _EvaluationEnvironment(_elementMap, _environment), |
| 1521 constantSystem); |
1508 }); | 1522 }); |
1509 } | 1523 } |
1510 | 1524 |
1511 @override | 1525 @override |
1512 bool hasConstantValue(ConstantExpression expression) { | 1526 bool hasConstantValue(ConstantExpression expression) { |
1513 throw new UnimplementedError("KernelConstantEnvironment.hasConstantValue"); | 1527 throw new UnimplementedError("KernelConstantEnvironment.hasConstantValue"); |
1514 } | 1528 } |
1515 } | 1529 } |
1516 | 1530 |
1517 /// Evaluation environment used for computing [ConstantValue]s for | 1531 /// Evaluation environment used for computing [ConstantValue]s for |
1518 /// kernel based [ConstantExpression]s. | 1532 /// kernel based [ConstantExpression]s. |
1519 class _EvaluationEnvironment implements EvaluationEnvironment { | 1533 class _EvaluationEnvironment implements EvaluationEnvironment { |
1520 final KernelToElementMapImpl _elementMap; | 1534 final KernelToElementMapBase _elementMap; |
| 1535 final Environment _environment; |
1521 | 1536 |
1522 _EvaluationEnvironment(this._elementMap); | 1537 _EvaluationEnvironment(this._elementMap, this._environment); |
1523 | 1538 |
1524 @override | 1539 @override |
1525 CommonElements get commonElements => _elementMap.commonElements; | 1540 CommonElements get commonElements => _elementMap.commonElements; |
1526 | 1541 |
1527 @override | 1542 @override |
1528 InterfaceType substByContext(InterfaceType base, InterfaceType target) { | 1543 InterfaceType substByContext(InterfaceType base, InterfaceType target) { |
1529 return _elementMap._substByContext(base, target); | 1544 return _elementMap._substByContext(base, target); |
1530 } | 1545 } |
1531 | 1546 |
1532 @override | 1547 @override |
1533 ConstantConstructor getConstructorConstant(ConstructorEntity constructor) { | 1548 ConstantConstructor getConstructorConstant(ConstructorEntity constructor) { |
1534 return _elementMap._getConstructorConstant(constructor); | 1549 return _elementMap._getConstructorConstant(constructor); |
1535 } | 1550 } |
1536 | 1551 |
1537 @override | 1552 @override |
1538 ConstantExpression getFieldConstant(FieldEntity field) { | 1553 ConstantExpression getFieldConstant(FieldEntity field) { |
1539 return _elementMap._getFieldConstant(field); | 1554 return _elementMap._getFieldConstant(field); |
1540 } | 1555 } |
1541 | 1556 |
1542 @override | 1557 @override |
1543 ConstantExpression getLocalConstant(Local local) { | 1558 ConstantExpression getLocalConstant(Local local) { |
1544 throw new UnimplementedError("_EvaluationEnvironment.getLocalConstant"); | 1559 throw new UnimplementedError("_EvaluationEnvironment.getLocalConstant"); |
1545 } | 1560 } |
1546 | 1561 |
1547 @override | 1562 @override |
1548 String readFromEnvironment(String name) { | 1563 String readFromEnvironment(String name) { |
1549 return _elementMap._environment.valueOf(name); | 1564 return _environment.valueOf(name); |
1550 } | 1565 } |
1551 } | 1566 } |
1552 | 1567 |
1553 class KernelResolutionWorldBuilder extends KernelResolutionWorldBuilderBase { | 1568 class KernelResolutionWorldBuilder extends KernelResolutionWorldBuilderBase { |
1554 final KernelToElementMapImpl elementMap; | 1569 final KernelToElementMapImpl elementMap; |
1555 | 1570 |
1556 KernelResolutionWorldBuilder( | 1571 KernelResolutionWorldBuilder( |
1557 this.elementMap, | 1572 this.elementMap, |
1558 NativeBasicData nativeBasicData, | 1573 NativeBasicData nativeBasicData, |
1559 NativeDataBuilder nativeDataBuilder, | 1574 NativeDataBuilder nativeDataBuilder, |
(...skipping 227 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1787 } | 1802 } |
1788 | 1803 |
1789 class JsKernelToElementMap extends KernelToElementMapBase | 1804 class JsKernelToElementMap extends KernelToElementMapBase |
1790 with KernelToElementMapForBuildingMixin | 1805 with KernelToElementMapForBuildingMixin |
1791 implements KernelToWorldBuilder { | 1806 implements KernelToWorldBuilder { |
1792 final JsToFrontendMap _map; | 1807 final JsToFrontendMap _map; |
1793 final ElementEnvironment _elementEnvironment; | 1808 final ElementEnvironment _elementEnvironment; |
1794 final CommonElements _commonElements; | 1809 final CommonElements _commonElements; |
1795 final KernelToElementMapImpl _elementMap; | 1810 final KernelToElementMapImpl _elementMap; |
1796 | 1811 |
1797 JsKernelToElementMap(this._map, this._elementEnvironment, | 1812 JsKernelToElementMap( |
1798 this._commonElements, this._elementMap); | 1813 DiagnosticReporter reporter, |
| 1814 Environment environment, |
| 1815 this._map, |
| 1816 this._elementEnvironment, |
| 1817 this._commonElements, |
| 1818 this._elementMap) |
| 1819 : super(reporter, environment); |
1799 | 1820 |
1800 @override | 1821 @override |
1801 Spannable getSpannable(MemberEntity member, ir.Node node) { | 1822 Spannable getSpannable(MemberEntity member, ir.Node node) { |
1802 return _elementMap.getSpannable(_map.toFrontendMember(member), node); | 1823 return _elementMap.getSpannable(_map.toFrontendMember(member), node); |
1803 } | 1824 } |
1804 | 1825 |
1805 @override | 1826 @override |
1806 LibraryEntity getLibrary(ir.Library node) { | 1827 LibraryEntity getLibrary(ir.Library node) { |
1807 return _map.toBackendLibrary(_elementMap.getLibrary(node)); | 1828 return _map.toBackendLibrary(_elementMap.getLibrary(node)); |
1808 } | 1829 } |
(...skipping 104 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1913 throw new UnsupportedError( | 1934 throw new UnsupportedError( |
1914 "JsKernelToElementMap.getConstantFieldInitializer"); | 1935 "JsKernelToElementMap.getConstantFieldInitializer"); |
1915 } | 1936 } |
1916 | 1937 |
1917 @override | 1938 @override |
1918 bool hasConstantFieldInitializer(FieldEntity field) { | 1939 bool hasConstantFieldInitializer(FieldEntity field) { |
1919 throw new UnsupportedError( | 1940 throw new UnsupportedError( |
1920 "JsKernelToElementMap.hasConstantFieldInitializer"); | 1941 "JsKernelToElementMap.hasConstantFieldInitializer"); |
1921 } | 1942 } |
1922 } | 1943 } |
OLD | NEW |