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

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

Issue 2829223007: Introduce initial plumbing for type promotion in fasta. (Closed)
Patch Set: Add missing copyrights Created 3 years, 8 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`.
11 /// 11 ///
12 /// Note that these classes represent the Dart language prior to desugaring. 12 /// Note that these classes represent the Dart language prior to desugaring.
13 /// When a single Dart construct desugars to a tree containing multiple kernel 13 /// When a single Dart construct desugars to a tree containing multiple kernel
14 /// AST nodes, the shadow class extends the kernel object at the top of the 14 /// AST nodes, the shadow class extends the kernel object at the top of the
15 /// desugared tree. 15 /// desugared tree.
16 /// 16 ///
17 /// This means that in some cases multiple shadow classes may extend the same 17 /// This means that in some cases multiple shadow classes may extend the same
18 /// kernel class, because multiple constructs in Dart may desugar to a tree 18 /// kernel class, because multiple constructs in Dart may desugar to a tree
19 /// with the same kind of root node. 19 /// with the same kind of root node.
20 import 'package:front_end/src/base/instrumentation.dart'; 20 import 'package:front_end/src/base/instrumentation.dart';
21 import 'package:front_end/src/fasta/type_inference/type_inference_engine.dart'; 21 import 'package:front_end/src/fasta/type_inference/type_inference_engine.dart';
22 import 'package:front_end/src/fasta/type_inference/type_inferrer.dart'; 22 import 'package:front_end/src/fasta/type_inference/type_inferrer.dart';
23 import 'package:front_end/src/fasta/type_inference/type_promotion.dart';
23 import 'package:kernel/ast.dart'; 24 import 'package:kernel/ast.dart';
24 25
25 /// Concrete shadow object representing a statement block in kernel form. 26 /// Concrete shadow object representing a statement block in kernel form.
26 class KernelBlock extends Block implements KernelStatement { 27 class KernelBlock extends Block implements KernelStatement {
27 KernelBlock(List<Statement> statements) : super(statements); 28 KernelBlock(List<Statement> statements) : super(statements);
28 29
29 @override 30 @override
30 void _inferStatement(KernelTypeInferrer inferrer) { 31 void _inferStatement(KernelTypeInferrer inferrer) {
31 for (var statement in statements) { 32 for (var statement in statements) {
32 inferrer.inferStatement(statement); 33 inferrer.inferStatement(statement);
33 } 34 }
34 } 35 }
35 } 36 }
36 37
37 /// Common base class for shadow objects representing expressions in kernel 38 /// Common base class for shadow objects representing expressions in kernel
38 /// form. 39 /// form.
39 abstract class KernelExpression implements Expression { 40 abstract class KernelExpression implements Expression {
40 /// Calls back to [inferrer] to perform type inference for whatever concrete 41 /// Calls back to [inferrer] to perform type inference for whatever concrete
41 /// type of [KernelExpression] this is. 42 /// type of [KernelExpression] this is.
42 DartType _inferExpression( 43 DartType _inferExpression(
43 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded); 44 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded);
44 } 45 }
45 46
47 /// Concrete shadow object representing an expression statement in kernel form.
48 class KernelExpressionStatement extends ExpressionStatement
49 implements KernelStatement {
50 KernelExpressionStatement(Expression expression) : super(expression);
51
52 @override
53 void _inferStatement(KernelTypeInferrer inferrer) {
54 inferrer.inferExpressionStatement(expression);
55 }
56 }
57
46 /// Concrete shadow object representing a field in kernel form. 58 /// Concrete shadow object representing a field in kernel form.
47 class KernelField extends Field { 59 class KernelField extends Field {
48 bool _implicitlyTyped = true; 60 bool _implicitlyTyped = true;
49 61
50 FieldNode<KernelField> _fieldNode; 62 FieldNode<KernelField> _fieldNode;
51 63
52 bool _isInferred = false; 64 bool _isInferred = false;
53 65
54 KernelTypeInferrer _typeInferrer; 66 KernelTypeInferrer _typeInferrer;
55 67
(...skipping 20 matching lines...) Expand all
76 } 88 }
77 89
78 /// Concrete shadow object representing a function expression in kernel form. 90 /// Concrete shadow object representing a function expression in kernel form.
79 class KernelFunctionExpression extends FunctionExpression 91 class KernelFunctionExpression extends FunctionExpression
80 implements KernelExpression { 92 implements KernelExpression {
81 KernelFunctionExpression(FunctionNode function) : super(function); 93 KernelFunctionExpression(FunctionNode function) : super(function);
82 94
83 @override 95 @override
84 DartType _inferExpression( 96 DartType _inferExpression(
85 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded) { 97 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded) {
86 // TODO(paulberry): implement. 98 var asyncMarker = function.asyncMarker;
87 return typeNeeded ? const DynamicType() : null; 99 bool isAsync = asyncMarker == AsyncMarker.Async ||
100 asyncMarker == AsyncMarker.AsyncStar;
101 bool isGenerator = asyncMarker == AsyncMarker.SyncStar ||
102 asyncMarker == AsyncMarker.AsyncStar;
103 return inferrer.inferFunctionExpression(
104 typeContext,
105 typeNeeded,
106 function.body,
107 function.body is ReturnStatement,
108 isAsync,
109 isGenerator,
110 fileOffset, (type) {
111 function.returnType = type;
112 }, () => function.functionType);
88 } 113 }
89 } 114 }
90 115
116 /// Concrete shadow object representing an if statement in kernel form.
117 class KernelIfStatement extends IfStatement implements KernelStatement {
118 KernelIfStatement(Expression condition, Statement then, Statement otherwise)
119 : super(condition, then, otherwise);
120
121 @override
122 void _inferStatement(KernelTypeInferrer inferrer) {
123 inferrer.inferIfStatement(condition, then, otherwise);
124 }
125 }
126
91 /// Concrete shadow object representing an integer literal in kernel form. 127 /// Concrete shadow object representing an integer literal in kernel form.
92 class KernelIntLiteral extends IntLiteral implements KernelExpression { 128 class KernelIntLiteral extends IntLiteral implements KernelExpression {
93 KernelIntLiteral(int value) : super(value); 129 KernelIntLiteral(int value) : super(value);
94 130
95 @override 131 @override
96 DartType _inferExpression( 132 DartType _inferExpression(
97 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded) { 133 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded) {
98 return inferrer.inferIntLiteral(typeContext, typeNeeded); 134 return inferrer.inferIntLiteral(typeContext, typeNeeded);
99 } 135 }
100 } 136 }
101 137
138 /// Concrete shadow object representing a non-inverted "is" test in kernel form.
139 class KernelIsExpression extends IsExpression implements KernelExpression {
140 KernelIsExpression(Expression operand, DartType type) : super(operand, type);
141
142 @override
143 DartType _inferExpression(
144 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded) {
145 return inferrer.inferIsExpression(typeContext, typeNeeded, operand);
146 }
147 }
148
149 /// Concrete shadow object representing an inverted "is" test in kernel form.
150 class KernelIsNotExpression extends Not implements KernelExpression {
151 KernelIsNotExpression(Expression operand, DartType type, int charOffset)
152 : super(new IsExpression(operand, type)..fileOffset = charOffset);
153
154 @override
155 DartType _inferExpression(
156 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded) {
157 IsExpression isExpression = this.operand;
158 return inferrer.inferIsExpression(
159 typeContext, typeNeeded, isExpression.operand);
160 }
161 }
162
102 /// Concrete shadow object representing a list literal in kernel form. 163 /// Concrete shadow object representing a list literal in kernel form.
103 class KernelListLiteral extends ListLiteral implements KernelExpression { 164 class KernelListLiteral extends ListLiteral implements KernelExpression {
104 KernelListLiteral(List<KernelExpression> expressions, 165 KernelListLiteral(List<KernelExpression> expressions,
105 {DartType typeArgument, bool isConst: false}) 166 {DartType typeArgument, bool isConst: false})
106 : super(expressions, typeArgument: typeArgument, isConst: isConst); 167 : super(expressions, typeArgument: typeArgument, isConst: isConst);
107 168
108 @override 169 @override
109 DartType _inferExpression( 170 DartType _inferExpression(
110 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded) { 171 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded) {
111 // TODO(paulberry): implement. 172 // TODO(paulberry): implement.
(...skipping 107 matching lines...) Expand 10 before | Expand all | Expand 10 after
219 280
220 @override 281 @override
221 void setFieldInferredType(KernelField field, DartType inferredType) { 282 void setFieldInferredType(KernelField field, DartType inferredType) {
222 field._setInferredType(inferredType); 283 field._setInferredType(inferredType);
223 } 284 }
224 } 285 }
225 286
226 /// Concrete implementation of [TypeInferrer] specialized to work with kernel 287 /// Concrete implementation of [TypeInferrer] specialized to work with kernel
227 /// objects. 288 /// objects.
228 class KernelTypeInferrer extends TypeInferrerImpl<Statement, Expression, 289 class KernelTypeInferrer extends TypeInferrerImpl<Statement, Expression,
229 KernelVariableDeclaration, KernelField> { 290 VariableDeclaration, KernelField> {
291 @override
292 final typePromoter = new KernelTypePromoter();
293
230 KernelTypeInferrer._(KernelTypeInferenceEngine engine, String uri) 294 KernelTypeInferrer._(KernelTypeInferenceEngine engine, String uri)
231 : super(engine, uri); 295 : super(engine, uri);
232 296
233 @override 297 @override
234 Expression getFieldInitializer(KernelField field) { 298 Expression getFieldInitializer(KernelField field) {
235 return field.initializer; 299 return field.initializer;
236 } 300 }
237 301
238 @override 302 @override
239 FieldNode<KernelField> getFieldNodeForReadTarget(Member readTarget) { 303 FieldNode<KernelField> getFieldNodeForReadTarget(Member readTarget) {
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after
280 return statement._inferStatement(this); 344 return statement._inferStatement(this);
281 } else { 345 } else {
282 // Encountered a statement type for which type inference is not yet 346 // Encountered a statement type for which type inference is not yet
283 // implemented, so just skip it for now. 347 // implemented, so just skip it for now.
284 // TODO(paulberry): once the BodyBuilder uses shadow classes for 348 // TODO(paulberry): once the BodyBuilder uses shadow classes for
285 // everything, this case should no longer be needed. 349 // everything, this case should no longer be needed.
286 } 350 }
287 } 351 }
288 } 352 }
289 353
354 /// Concrete implementation of [TypePromoter] specialized to work with kernel
355 /// objects.
356 ///
357 /// Note: the second type parameter really ought to be
358 /// KernelVariableDeclaration, but we can't do that yet because BodyBuilder
359 /// still uses raw VariableDeclaration objects sometimes.
360 /// TODO(paulberry): fix this.
361 class KernelTypePromoter
362 extends TypePromoterImpl<Expression, VariableDeclaration> {
363 @override
364 int getVariableFunctionNestingLevel(VariableDeclaration variable) {
365 if (variable is KernelVariableDeclaration) {
366 return variable._functionNestingLevel;
367 } else {
368 // Hack to deal with the fact that BodyBuilder still creates raw
369 // VariableDeclaration objects sometimes.
370 // TODO(paulberry): get rid of this once the type parameter is
371 // KernelVariableDeclaration.
372 return 0;
373 }
374 }
375
376 @override
377 bool sameExpressions(Expression a, Expression b) {
378 return identical(a, b);
379 }
380
381 @override
382 void setVariableMutatedAnywhere(VariableDeclaration variable) {
383 if (variable is KernelVariableDeclaration) {
384 variable._mutatedAnywhere = true;
385 } else {
386 // Hack to deal with the fact that BodyBuilder still creates raw
387 // VariableDeclaration objects sometimes.
388 // TODO(paulberry): get rid of this once the type parameter is
389 // KernelVariableDeclaration.
390 }
391 }
392
393 @override
394 void setVariableMutatedInClosure(VariableDeclaration variable) {
395 if (variable is KernelVariableDeclaration) {
396 variable._mutatedInClosure = true;
397 } else {
398 // Hack to deal with the fact that BodyBuilder still creates raw
399 // VariableDeclaration objects sometimes.
400 // TODO(paulberry): get rid of this once the type parameter is
401 // KernelVariableDeclaration.
402 }
403 }
404
405 @override
406 bool wasVariableMutatedAnywhere(VariableDeclaration variable) {
407 if (variable is KernelVariableDeclaration) {
408 return variable._mutatedAnywhere;
409 } else {
410 // Hack to deal with the fact that BodyBuilder still creates raw
411 // VariableDeclaration objects sometimes.
412 // TODO(paulberry): get rid of this once the type parameter is
413 // KernelVariableDeclaration.
414 return true;
415 }
416 }
417 }
418
290 /// Concrete shadow object representing a variable declaration in kernel form. 419 /// Concrete shadow object representing a variable declaration in kernel form.
291 class KernelVariableDeclaration extends VariableDeclaration 420 class KernelVariableDeclaration extends VariableDeclaration
292 implements KernelStatement { 421 implements KernelStatement {
293 final bool _implicitlyTyped; 422 final bool _implicitlyTyped;
294 423
295 KernelVariableDeclaration(String name, 424 final int _functionNestingLevel;
425
426 bool _mutatedInClosure = false;
427
428 bool _mutatedAnywhere = false;
429
430 KernelVariableDeclaration(String name, this._functionNestingLevel,
296 {Expression initializer, 431 {Expression initializer,
297 DartType type, 432 DartType type,
298 bool isFinal: false, 433 bool isFinal: false,
299 bool isConst: false}) 434 bool isConst: false})
300 : _implicitlyTyped = type == null, 435 : _implicitlyTyped = type == null,
301 super(name, 436 super(name,
302 initializer: initializer, 437 initializer: initializer,
303 type: type ?? const DynamicType(), 438 type: type ?? const DynamicType(),
304 isFinal: isFinal, 439 isFinal: isFinal,
305 isConst: isConst); 440 isConst: isConst);
306 441
442 DartType get _declaredType => _implicitlyTyped ? null : type;
443
307 @override 444 @override
308 void _inferStatement(KernelTypeInferrer inferrer) { 445 void _inferStatement(KernelTypeInferrer inferrer) {
309 inferrer.inferVariableDeclaration( 446 inferrer.inferVariableDeclaration(
310 _implicitlyTyped ? null : type, initializer, fileOffset, (type) { 447 _implicitlyTyped ? null : type, initializer, fileOffset, (type) {
311 this.type = type; 448 this.type = type;
312 }); 449 });
313 } 450 }
314 } 451 }
315 452
316 /// Concrete shadow object representing a read from a variable in kernel form. 453 /// Concrete shadow object representing a read from a variable in kernel form.
317 class KernelVariableGet extends VariableGet implements KernelExpression { 454 class KernelVariableGet extends VariableGet implements KernelExpression {
318 KernelVariableGet(VariableDeclaration variable, [DartType promotedType]) 455 final TypePromotionFact<VariableDeclaration> _fact;
319 : super(variable, promotedType); 456
457 final TypePromotionScope _scope;
458
459 KernelVariableGet(VariableDeclaration variable, this._fact, this._scope)
460 : super(variable);
320 461
321 @override 462 @override
322 DartType _inferExpression( 463 DartType _inferExpression(
323 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded) { 464 KernelTypeInferrer inferrer, DartType typeContext, bool typeNeeded) {
324 // TODO(paulberry): implement. 465 bool mutatedInClosure;
325 return typeNeeded ? const DynamicType() : null; 466 DartType declaredType;
467 var variable = this.variable;
468 if (variable is KernelVariableDeclaration) {
469 mutatedInClosure = variable._mutatedInClosure;
470 declaredType = variable._declaredType;
471 } else {
472 // Hack to deal with the fact that BodyBuilder still creates raw
473 // VariableDeclaration objects sometimes.
474 // TODO(paulberry): get rid of this once the type parameter is
475 // KernelVariableDeclaration.
476 mutatedInClosure = true;
477 declaredType = variable.type;
478 }
479 return inferrer.inferVariableGet(typeContext, typeNeeded, mutatedInClosure,
480 _fact, _scope, fileOffset, declaredType, (type) {
481 promotedType = type;
482 });
326 } 483 }
327 } 484 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698