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

Side by Side Diff: pkg/front_end/lib/src/fasta/kernel/kernel_shadow_ast.dart

Issue 2942623004: Fuse top level type inference with dependency generation. (Closed)
Patch Set: Created 3 years, 6 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
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 /// This file declares a "shadow hierarchy" of concrete classes which extend 5 /// This file declares a "shadow hierarchy" of concrete classes which extend
6 /// the kernel class hierarchy, adding methods and fields needed by the 6 /// the kernel class hierarchy, adding methods and fields needed by the
7 /// BodyBuilder. 7 /// BodyBuilder.
8 /// 8 ///
9 /// Instances of these classes may be created using the factory methods in 9 /// Instances of these classes may be created using the factory methods in
10 /// `ast_factory.dart`. 10 /// `ast_factory.dart`.
(...skipping 353 matching lines...) Expand 10 before | Expand all | Expand 10 after
364 inferrer.findMethodInvocationMember(writeContext, equalsInvocation, 364 inferrer.findMethodInvocationMember(writeContext, equalsInvocation,
365 silent: true); 365 silent: true);
366 return inferrer.typeSchemaEnvironment 366 return inferrer.typeSchemaEnvironment
367 .getLeastUpperBound(inferredType, rhsType); 367 .getLeastUpperBound(inferredType, rhsType);
368 } else if (combiner != null) { 368 } else if (combiner != null) {
369 bool isOverloadedArithmeticOperator = false; 369 bool isOverloadedArithmeticOperator = false;
370 var combinerMember = inferrer 370 var combinerMember = inferrer
371 .findMethodInvocationMember(writeContext, combiner, silent: true); 371 .findMethodInvocationMember(writeContext, combiner, silent: true);
372 if (combinerMember is Procedure) { 372 if (combinerMember is Procedure) {
373 isOverloadedArithmeticOperator = inferrer.typeSchemaEnvironment 373 isOverloadedArithmeticOperator = inferrer.typeSchemaEnvironment
374 .isOverloadedArithmeticOperator(combinerMember); 374 .isOverloadedArithmeticOperatorAndType(
375 combinerMember, writeContext);
375 } 376 }
376 if (isPostIncDec) { 377 if (isPostIncDec) {
377 return inferredType; 378 return inferredType;
378 } else { 379 } else {
379 DartType rhsType; 380 DartType rhsType;
380 if (isPreIncDec) { 381 if (isPreIncDec) {
381 rhsType = inferrer.coreTypes.intClass.rawType; 382 rhsType = inferrer.coreTypes.intClass.rawType;
382 } else { 383 } else {
383 // Analyzer uses a null context for the RHS here. 384 // Analyzer uses a null context for the RHS here.
384 // TODO(paulberry): improve on this. 385 // TODO(paulberry): improve on this.
(...skipping 294 matching lines...) Expand 10 before | Expand all | Expand 10 after
679 arguments); 680 arguments);
680 inferrer.listener.constructorInvocationExit(this, inferredType); 681 inferrer.listener.constructorInvocationExit(this, inferredType);
681 return inferredType; 682 return inferredType;
682 } 683 }
683 } 684 }
684 685
685 /// Concrete shadow object representing a field in kernel form. 686 /// Concrete shadow object representing a field in kernel form.
686 class KernelField extends Field { 687 class KernelField extends Field {
687 FieldNode _fieldNode; 688 FieldNode _fieldNode;
688 689
689 bool _isInferred = false;
690
691 KernelTypeInferrer _typeInferrer; 690 KernelTypeInferrer _typeInferrer;
692 691
693 KernelField(Name name, {String fileUri}) : super(name, fileUri: fileUri) {} 692 KernelField(Name name, {String fileUri}) : super(name, fileUri: fileUri) {}
694
695 void _setInferredType(DartType inferredType) {
696 _isInferred = true;
697 super.type = inferredType;
698 }
699 } 693 }
700 694
701 /// Concrete shadow object representing a for-in loop in kernel form. 695 /// Concrete shadow object representing a for-in loop in kernel form.
702 class KernelForInStatement extends ForInStatement implements KernelStatement { 696 class KernelForInStatement extends ForInStatement implements KernelStatement {
703 final bool _declaresVariable; 697 final bool _declaresVariable;
704 698
705 KernelForInStatement(VariableDeclaration variable, Expression iterable, 699 KernelForInStatement(VariableDeclaration variable, Expression iterable,
706 Statement body, this._declaresVariable, 700 Statement body, this._declaresVariable,
707 {bool isAsync: false}) 701 {bool isAsync: false})
708 : super(variable, iterable, body, isAsync: isAsync); 702 : super(variable, iterable, body, isAsync: isAsync);
(...skipping 596 matching lines...) Expand 10 before | Expand all | Expand 10 after
1305 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded) { 1299 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded) {
1306 typeNeeded = inferrer.listener.methodInvocationEnter(this, typeContext) || 1300 typeNeeded = inferrer.listener.methodInvocationEnter(this, typeContext) ||
1307 typeNeeded; 1301 typeNeeded;
1308 // First infer the receiver so we can look up the method that was invoked. 1302 // First infer the receiver so we can look up the method that was invoked.
1309 var receiverType = inferrer.inferExpression(receiver, null, true); 1303 var receiverType = inferrer.inferExpression(receiver, null, true);
1310 bool isOverloadedArithmeticOperator = false; 1304 bool isOverloadedArithmeticOperator = false;
1311 Member interfaceMember = 1305 Member interfaceMember =
1312 inferrer.findMethodInvocationMember(receiverType, this); 1306 inferrer.findMethodInvocationMember(receiverType, this);
1313 if (interfaceMember is Procedure) { 1307 if (interfaceMember is Procedure) {
1314 isOverloadedArithmeticOperator = inferrer.typeSchemaEnvironment 1308 isOverloadedArithmeticOperator = inferrer.typeSchemaEnvironment
1315 .isOverloadedArithmeticOperator(interfaceMember); 1309 .isOverloadedArithmeticOperatorAndType(interfaceMember, receiverType);
1316 } 1310 }
1317 var calleeType = inferrer.getCalleeFunctionType( 1311 var calleeType = inferrer.getCalleeFunctionType(
1318 interfaceMember, receiverType, name, !_isImplicitCall); 1312 interfaceMember, receiverType, name, !_isImplicitCall);
1319 bool forceArgumentInference = false; 1313 bool forceArgumentInference = false;
1320 if (inferrer.isDryRun) { 1314 if (inferrer.isDryRun) {
1321 if (_isUserDefinableOperator(name.name)) { 1315 if (_isUserDefinableOperator(name.name)) {
1322 // If this is an overloadable arithmetic operator, then type inference 1316 // If this is an overloadable arithmetic operator, then type inference
1323 // might depend on the RHS, so conservatively assume it does. 1317 // might depend on the RHS, so conservatively assume it does.
1324 forceArgumentInference = _isOverloadableArithmeticOperator(name.name); 1318 forceArgumentInference = _isOverloadableArithmeticOperator(name.name);
1325 } else { 1319 } else {
(...skipping 262 matching lines...) Expand 10 before | Expand all | Expand 10 after
1588 DartType _inferExpression( 1582 DartType _inferExpression(
1589 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded) { 1583 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded) {
1590 typeNeeded = inferrer.listener.staticAssignEnter(desugared, typeContext) || 1584 typeNeeded = inferrer.listener.staticAssignEnter(desugared, typeContext) ||
1591 typeNeeded; 1585 typeNeeded;
1592 // TODO(paulberry): record the appropriate types on let variables and 1586 // TODO(paulberry): record the appropriate types on let variables and
1593 // conditional expressions. 1587 // conditional expressions.
1594 DartType writeContext; 1588 DartType writeContext;
1595 var write = this.write; 1589 var write = this.write;
1596 if (write is StaticSet) { 1590 if (write is StaticSet) {
1597 writeContext = write.target.setterType; 1591 writeContext = write.target.setterType;
1598 if (inferrer.isDryRun) { 1592 var target = write.target;
1599 var target = write.target; 1593 if (target is KernelField && target._fieldNode != null) {
1600 if (target is KernelField && target._fieldNode != null) { 1594 if (inferrer.isDryRun) {
1601 inferrer.recordDryRunDependency(target._fieldNode); 1595 inferrer.recordDryRunDependency(target._fieldNode);
1602 } 1596 }
1597 if (TypeInferenceEngineImpl.fusedTopLevelInference &&
1598 inferrer.isTopLevel) {
1599 inferrer.engine
1600 .inferFieldFused(target._fieldNode, inferrer.fieldNode);
1601 }
1603 } 1602 }
1604 } 1603 }
1605 var inferredType = _inferRhs(inferrer, writeContext); 1604 var inferredType = _inferRhs(inferrer, writeContext);
1606 inferrer.listener.staticAssignExit(desugared, inferredType); 1605 inferrer.listener.staticAssignExit(desugared, inferredType);
1607 return inferredType; 1606 return inferredType;
1608 } 1607 }
1609 } 1608 }
1610 1609
1611 /// Concrete shadow object representing a read of a static variable in kernel 1610 /// Concrete shadow object representing a read of a static variable in kernel
1612 /// form. 1611 /// form.
(...skipping 17 matching lines...) Expand all
1630 if (target is KernelField && target._fieldNode != null) { 1629 if (target is KernelField && target._fieldNode != null) {
1631 collector.recordDependency(target._fieldNode); 1630 collector.recordDependency(target._fieldNode);
1632 } 1631 }
1633 } 1632 }
1634 1633
1635 @override 1634 @override
1636 DartType _inferExpression( 1635 DartType _inferExpression(
1637 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded) { 1636 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded) {
1638 typeNeeded = 1637 typeNeeded =
1639 inferrer.listener.staticGetEnter(this, typeContext) || typeNeeded; 1638 inferrer.listener.staticGetEnter(this, typeContext) || typeNeeded;
1640 if (inferrer.isDryRun) { 1639 var target = this.target;
1641 var target = this.target; 1640 if (target is KernelField && target._fieldNode != null) {
1642 if (target is KernelField && target._fieldNode != null) { 1641 if (inferrer.isDryRun) {
1643 inferrer.recordDryRunDependency(target._fieldNode); 1642 inferrer.recordDryRunDependency(target._fieldNode);
1644 } 1643 }
1644 if (TypeInferenceEngineImpl.fusedTopLevelInference &&
1645 inferrer.isTopLevel) {
1646 inferrer.engine.inferFieldFused(target._fieldNode, inferrer.fieldNode);
1647 }
1645 } 1648 }
1646 var inferredType = typeNeeded ? target.getterType : null; 1649 var inferredType = typeNeeded ? target.getterType : null;
1647 inferrer.listener.staticGetExit(this, inferredType); 1650 inferrer.listener.staticGetExit(this, inferredType);
1648 return inferredType; 1651 return inferredType;
1649 } 1652 }
1650 } 1653 }
1651 1654
1652 /// Shadow object for [StaticInvocation]. 1655 /// Shadow object for [StaticInvocation].
1653 class KernelStaticInvocation extends StaticInvocation 1656 class KernelStaticInvocation extends StaticInvocation
1654 implements KernelExpression { 1657 implements KernelExpression {
(...skipping 233 matching lines...) Expand 10 before | Expand all | Expand 10 after
1888 FieldNode createFieldNode(KernelField field) { 1891 FieldNode createFieldNode(KernelField field) {
1889 FieldNode fieldNode = new FieldNode(this, field); 1892 FieldNode fieldNode = new FieldNode(this, field);
1890 field._fieldNode = fieldNode; 1893 field._fieldNode = fieldNode;
1891 return fieldNode; 1894 return fieldNode;
1892 } 1895 }
1893 1896
1894 @override 1897 @override
1895 KernelTypeInferrer createLocalTypeInferrer( 1898 KernelTypeInferrer createLocalTypeInferrer(
1896 Uri uri, TypeInferenceListener listener, InterfaceType thisType) { 1899 Uri uri, TypeInferenceListener listener, InterfaceType thisType) {
1897 return new KernelTypeInferrer._( 1900 return new KernelTypeInferrer._(
1898 this, uri.toString(), listener, false, thisType); 1901 this, uri.toString(), listener, false, thisType, null);
1899 } 1902 }
1900 1903
1901 @override 1904 @override
1902 KernelTypeInferrer createTopLevelTypeInferrer(TypeInferenceListener listener, 1905 KernelTypeInferrer createTopLevelTypeInferrer(TypeInferenceListener listener,
1903 InterfaceType thisType, KernelField field) { 1906 InterfaceType thisType, KernelField field) {
1904 return field._typeInferrer = 1907 return field._typeInferrer = new KernelTypeInferrer._(
1905 new KernelTypeInferrer._(this, field.fileUri, listener, true, thisType); 1908 this, field.fileUri, listener, true, thisType, field._fieldNode);
1906 } 1909 }
1907 1910
1908 @override 1911 @override
1909 int getFieldOffset(KernelField field) { 1912 int getFieldOffset(KernelField field) {
1910 return field.fileOffset; 1913 return field.fileOffset;
1911 } 1914 }
1912 1915
1913 @override 1916 @override
1914 KernelTypeInferrer getFieldTypeInferrer(KernelField field) { 1917 KernelTypeInferrer getFieldTypeInferrer(KernelField field) {
1915 return field._typeInferrer; 1918 return field._typeInferrer;
1916 } 1919 }
1917
1918 @override
1919 bool isFieldInferred(KernelField field) {
1920 return field._isInferred;
1921 }
1922
1923 @override
1924 void setFieldInferredType(KernelField field, DartType inferredType) {
1925 field._setInferredType(inferredType);
1926 }
1927 } 1920 }
1928 1921
1929 /// Concrete implementation of [TypeInferrer] specialized to work with kernel 1922 /// Concrete implementation of [TypeInferrer] specialized to work with kernel
1930 /// objects. 1923 /// objects.
1931 class KernelTypeInferrer extends TypeInferrerImpl { 1924 class KernelTypeInferrer extends TypeInferrerImpl {
1932 @override 1925 @override
1933 final typePromoter = new KernelTypePromoter(); 1926 final typePromoter = new KernelTypePromoter();
1934 1927
1935 KernelTypeInferrer._(KernelTypeInferenceEngine engine, String uri, 1928 KernelTypeInferrer._(
1936 TypeInferenceListener listener, bool topLevel, InterfaceType thisType) 1929 KernelTypeInferenceEngine engine,
1937 : super(engine, uri, listener, topLevel, thisType); 1930 String uri,
1931 TypeInferenceListener listener,
1932 bool topLevel,
1933 InterfaceType thisType,
1934 FieldNode fieldNode)
1935 : super(engine, uri, listener, topLevel, thisType, fieldNode);
1938 1936
1939 @override 1937 @override
1940 Expression getFieldInitializer(KernelField field) { 1938 Expression getFieldInitializer(KernelField field) {
1941 return field.initializer; 1939 return field.initializer;
1942 } 1940 }
1943 1941
1944 @override 1942 @override
1945 DartType inferExpression( 1943 DartType inferExpression(
1946 Expression expression, DartType typeContext, bool typeNeeded) { 1944 Expression expression, DartType typeContext, bool typeNeeded) {
1947 // When doing top level inference, we skip subexpressions whose type isn't 1945 // When doing top level inference, we skip subexpressions whose type isn't
(...skipping 327 matching lines...) Expand 10 before | Expand all | Expand 10 after
2275 } 2273 }
2276 2274
2277 transformChildren(v) { 2275 transformChildren(v) {
2278 return internalError("Internal error: Unsupported operation."); 2276 return internalError("Internal error: Unsupported operation.");
2279 } 2277 }
2280 2278
2281 visitChildren(v) { 2279 visitChildren(v) {
2282 return internalError("Internal error: Unsupported operation."); 2280 return internalError("Internal error: Unsupported operation.");
2283 } 2281 }
2284 } 2282 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698