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

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

Issue 2628043005: Fasta kernel AST builder. (Closed)
Patch Set: Created 3 years, 11 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
(Empty)
1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file
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.
4
5 library fasta.builder_accessors;
6
7 export 'frontend_accessors.dart' show
8 wrapInvalid;
9
10 import 'frontend_accessors.dart' show
11 Accessor;
12
13 import 'package:kernel/ast.dart';
14
15 import 'package:kernel/core_types.dart' show
16 CoreTypes;
17
18 import '../errors.dart' show
19 internalError;
20
21 import 'frontend_accessors.dart' as kernel show
22 IndexAccessor,
23 NullAwarePropertyAccessor,
24 PropertyAccessor,
25 StaticAccessor,
26 SuperPropertyAccessor,
27 ThisIndexAccessor,
28 ThisPropertyAccessor,
29 VariableAccessor;
30
31 import 'frontend_accessors.dart' show
32 buildIsNull,
33 makeLet;
34
35 import 'kernel_builder.dart' show
36 Builder,
37 KernelClassBuilder,
38 PrefixBuilder,
39 TypeDeclarationBuilder;
40
41 abstract class BuilderHelper {
42 Uri get uri;
43
44 CoreTypes get coreTypes;
45
46 Constructor lookupConstructor(Name name, {bool isSuper});
47
48 Expression toSuperMethodInvocation(MethodInvocation node);
49
50 Expression toValue(node);
51
52 Member lookupSuperMember(Name name, {bool isSetter: false});
53
54 builderToFirstExpression(Builder builder, String name, int charOffset);
55
56 finishSend(Object receiver, Arguments arguments, int charOffset);
57
58 Expression buildCompileTimeError(error, [int charOffset]);
59
60 Initializer buildCompileTimeErrorIntializer(error, [int charOffset]);
61
62 Expression buildStaticInvocation(Procedure target, Arguments arguments);
63
64 Expression buildProblemExpression(Builder builder, String name);
65 }
66
67 abstract class BuilderAccessor implements Accessor {
68 BuilderHelper get helper;
69
70 int get charOffset;
71
72 String get plainNameForRead;
73
74 Uri get uri => helper.uri;
75
76 CoreTypes get coreTypes => helper.coreTypes;
77
78 String get plainNameForWrite => plainNameForRead;
79
80 Expression buildForEffect() => buildSimpleRead();
81
82 Initializer buildFieldInitializer(
83 Map<String, FieldInitializer> initializers) {
84 // TODO(ahe): This error message is really bad.
85 return helper.buildCompileTimeErrorIntializer(
86 "Can't use $plainNameForRead here.", charOffset);
87 }
88
89 Expression makeInvalidRead() {
90 return throwNoSuchMethodError(plainNameForRead, new Arguments.empty(), uri,
91 charOffset, coreTypes, isGetter: true);
92 }
93
94 Expression makeInvalidWrite(Expression value) {
95 return throwNoSuchMethodError(plainNameForWrite,
96 new Arguments(<Expression>[value]), uri, charOffset, coreTypes,
97 isSetter: true);
98 }
99
100 Expression doInvocation(int charOffset, Arguments arguments);
101
102 buildPropertyAccess(IncompleteSend send, bool isNullAware) {
103 if (send is SendAccessor) {
104 return buildMethodInvocation(buildSimpleRead(), send.name, send.arguments,
105 charOffset, isNullAware: isNullAware);
106 } else {
107 return PropertyAccessor.make(helper, charOffset, buildSimpleRead(),
108 send.name, null, null, isNullAware);
109 }
110 }
111
112 Expression buildThrowNoSuchMethodError(Arguments arguments) {
113 bool isGetter = false;
114 if (arguments == null) {
115 arguments = new Arguments.empty();
116 isGetter = true;
117 }
118 return throwNoSuchMethodError(plainNameForWrite, arguments, uri, charOffset,
119 coreTypes, isGetter: isGetter);
120 }
121
122 bool get isThisPropertyAccessor => false;
123 }
124
125 abstract class CompileTimeErrorAccessor implements Accessor {
126 Expression buildError();
127
128 Name get name => internalError("Unsupported operation.");
129
130 String get plainNameForRead => name.name;
131
132 withReceiver(Object receiver, {bool isNullAware}) => this;
133
134 Initializer buildFieldInitializer(
135 Map<String, FieldInitializer> initializers) {
136 return new LocalInitializer(new VariableDeclaration.forValue(buildError()));
137 }
138
139 doInvocation(int charOffset, Arguments arguments) => this;
140
141 buildPropertyAccess(IncompleteSend send, bool isNullAware) => this;
142
143 buildThrowNoSuchMethodError(Arguments arguments) => this;
144
145 Expression buildAssignment(Expression value, {bool voidContext: false}) {
146 return buildError();
147 }
148
149 Expression buildCompoundAssignment(Name binaryOperator, Expression value,
150 {bool voidContext: false, Procedure interfaceTarget}) {
151 return buildError();
152 }
153
154 Expression buildPrefixIncrement(Name binaryOperator,
155 {bool voidContext: false, Procedure interfaceTarget}) {
156 return buildError();
157 }
158
159 Expression buildPostfixIncrement(Name binaryOperator,
160 {bool voidContext: false, Procedure interfaceTarget}) {
161 return buildError();
162 }
163
164 Expression buildNullAwareAssignment(Expression value, DartType type,
165 {bool voidContext: false}) {
166 return buildError();
167 }
168
169 Expression buildSimpleRead() => buildError();
170
171 Expression makeInvalidRead() => buildError();
172
173 Expression makeInvalidWrite(Expression value) => buildError();
174 }
175
176 class ThisAccessor extends BuilderAccessor {
177 final BuilderHelper helper;
178
179 final int charOffset;
180
181 final bool isInitializer;
182
183 final bool isSuper;
184
185 ThisAccessor(this.helper, this.charOffset, this.isInitializer,
186 {this.isSuper: false});
187
188 String get plainNameForRead => internalError(isSuper ? "super" : "this");
189
190 Expression buildSimpleRead() {
191 if (!isSuper) {
192 return new ThisExpression();
193 } else {
194 return helper.buildCompileTimeError(
195 "Can't use `super` as an expression.", charOffset);
196 }
197 }
198
199 Initializer buildFieldInitializer(
200 Map<String, FieldInitializer> initializers) {
201 String keyword = isSuper ? "super" : "this";
202 return helper.buildCompileTimeErrorIntializer(
203 "Can't use '$keyword' here, did you mean '$keyword()'?", charOffset);
204 }
205
206 buildPropertyAccess(IncompleteSend send, bool isNullAware) {
207 if (isInitializer && send is SendAccessor) {
208 return buildConstructorInitializer(
209 send.charOffset, send.name, send.arguments);
210 }
211 if (send is SendAccessor) {
212 // Notice that 'this' or 'super' can't be null. So we can ignore the
213 // value of [isNullAware].
214 MethodInvocation result = buildMethodInvocation(new ThisExpression(),
215 send.name, send.arguments, charOffset);
216 return isSuper ? helper.toSuperMethodInvocation(result) : result;
217 } else {
218 if (isSuper) {
219 Member getter = helper.lookupSuperMember(send.name);
220 Member setter = helper.lookupSuperMember(send.name, isSetter: true);
221 return new SuperPropertyAccessor(helper, charOffset, send.name, getter,
222 setter);
223 } else {
224 return new ThisPropertyAccessor(helper, charOffset, send.name, null,
225 null);
226 }
227 }
228 }
229
230 doInvocation(int charOffset, Arguments arguments) {
231 if (isInitializer) {
232 return buildConstructorInitializer(charOffset, new Name(""), arguments);
233 } else {
234 return buildMethodInvocation(new ThisExpression(), new Name("call"),
235 arguments, charOffset);
236 }
237 }
238
239 Initializer buildConstructorInitializer(int charOffset, Name name,
240 Arguments arguments) {
241 Constructor constructor = helper.lookupConstructor(name, isSuper: isSuper);
242 Initializer result;
243 if (constructor == null) {
244 result = new LocalInitializer(
245 new VariableDeclaration.forValue(
246 throwNoSuchMethodError(
247 name.name, arguments, uri, charOffset, coreTypes,
248 isSuper: isSuper)));
249 } else if (isSuper) {
250 result = new SuperInitializer(constructor, arguments);
251 } else {
252 result = new RedirectingInitializer(constructor, arguments);
253 }
254 return result
255 ..fileOffset = charOffset;
256 }
257
258 Expression buildAssignment(Expression value, {bool voidContext: false}) {
259 return internalError("");
260 }
261
262 Expression buildNullAwareAssignment(Expression value, DartType type,
263 {bool voidContext: false}) {
264 return internalError("");
265 }
266
267 Expression buildCompoundAssignment(Name binaryOperator, Expression value,
268 {bool voidContext: false, Procedure interfaceTarget}) {
269 return internalError("");
270 }
271
272 Expression buildPrefixIncrement(Name binaryOperator,
273 {bool voidContext: false, Procedure interfaceTarget}) {
274 return internalError("");
275 }
276
277 Expression buildPostfixIncrement(Name binaryOperator,
278 {bool voidContext: false, Procedure interfaceTarget}) {
279 return internalError("");
280 }
281
282 toString() => "ThisAccessor($charOffset${isSuper ? ', super' : ''})";
283 }
284
285 abstract class IncompleteSend extends BuilderAccessor {
286 final BuilderHelper helper;
287
288 final int charOffset;
289
290 final Name name;
291
292 IncompleteSend(this.helper, this.charOffset, this.name);
293
294 withReceiver(Object receiver, {bool isNullAware});
295 }
296
297 class IncompleteError extends IncompleteSend with CompileTimeErrorAccessor {
298 final Object error;
299
300 IncompleteError(BuilderHelper helper, int charOffset, this.error)
301 : super(helper, charOffset, null);
302
303 Expression buildError() {
304 return helper.buildCompileTimeError(error, charOffset);
305 }
306 }
307
308 class SendAccessor extends IncompleteSend {
309 final Arguments arguments;
310
311 SendAccessor(BuilderHelper helper, int charOffset, Name name, this.arguments)
312 : super(helper, charOffset, name) {
313 assert(arguments != null);
314 }
315
316 String get plainNameForRead => name.name;
317
318 Expression buildSimpleRead() {
319 return internalError("Unhandled");
320 }
321
322 Expression buildAssignment(Expression value, {bool voidContext: false}) {
323 return internalError("Unhandled");
324 }
325
326 withReceiver(Object receiver, {bool isNullAware: false}) {
327 if (receiver is TypeDeclarationBuilder) {
328 /// For reasons beyond comprehension, `SomeType?.toString` is the same as
329 /// `SomeType.toString`, not `(SomeType).toString`. WTAF!?!
330 //
331 isNullAware = false;
332 }
333 if (receiver is BuilderAccessor) {
334 return receiver.buildPropertyAccess(this, isNullAware);
335 }
336 if (receiver is PrefixBuilder) {
337 PrefixBuilder prefix = receiver;
338 receiver = helper.builderToFirstExpression(
339 prefix.exports[name.name], "${prefix.name}.${name.name}", charOffset);
340 return helper.finishSend(receiver, arguments, charOffset);
341 }
342 Expression result;
343 if (receiver is KernelClassBuilder) {
344 Builder builder = receiver.findStaticBuilder(name.name);
345 if (builder == null) {
346 return buildThrowNoSuchMethodError(arguments);
347 }
348 if (builder.hasProblem) {
349 result = helper.buildProblemExpression(builder, name.name);
350 } else {
351 Member target = builder.target;
352 if (target != null) {
353 if (target is Field) {
354 result = buildMethodInvocation(new StaticGet(target),
355 new Name("call"), arguments, charOffset,
356 isNullAware: isNullAware);
357 } else {
358 result = helper.buildStaticInvocation(target, arguments);
359 }
360 } else {
361 result = buildThrowNoSuchMethodError(arguments);
362 }
363 }
364 } else {
365 result = buildMethodInvocation(helper.toValue(receiver), name,
366 arguments, charOffset, isNullAware: isNullAware);
367 }
368 return result..fileOffset = charOffset;
369 }
370
371 Expression buildNullAwareAssignment(Expression value, DartType type,
372 {bool voidContext: false}) {
373 return internalError("");
374 }
375
376 Expression buildCompoundAssignment(Name binaryOperator, Expression value,
377 {bool voidContext: false, Procedure interfaceTarget}) {
378 return internalError("");
379 }
380
381 Expression buildPrefixIncrement(Name binaryOperator,
382 {bool voidContext: false, Procedure interfaceTarget}) {
383 return internalError("Unhandled");
384 }
385
386 Expression buildPostfixIncrement(Name binaryOperator,
387 {bool voidContext: false, Procedure interfaceTarget}) {
388 return internalError("Unhandled");
389 }
390
391 Expression doInvocation(int charOffset, Arguments arguments) {
392 return internalError("Unhandled");
393 }
394
395 toString() => "SendAccessor($charOffset, $name, $arguments)";
396 }
397
398 class IncompletePropertyAccessor extends IncompleteSend {
399 IncompletePropertyAccessor(BuilderHelper helper, int charOffset, Name name)
400 : super(helper, charOffset, name);
401
402 String get plainNameForRead => name.name;
403
404 Expression buildSimpleRead() => internalError("Unhandled");
405
406 Expression buildAssignment(Expression value, {bool voidContext: false}) {
407 return internalError("Unhandled");
408 }
409
410 withReceiver(Object receiver, {bool isNullAware: false}) {
411 if (receiver is TypeDeclarationBuilder) {
412 /// For reasons beyond comprehension, `SomeType?.toString` is the same as
413 /// `SomeType.toString`, not `(SomeType).toString`. WTAF!?!
asgerf 2017/01/13 18:39:07 I agree, but let's not write comments like this.
ahe 2017/01/16 08:32:09 Done.
414 //
415 isNullAware = false;
416 }
417 if (receiver is BuilderAccessor) {
418 return receiver.buildPropertyAccess(this, isNullAware);
419 }
420 if (receiver is PrefixBuilder) {
421 PrefixBuilder prefix = receiver;
422 return helper.builderToFirstExpression(
423 prefix.exports[name.name], name.name, charOffset);
424 }
425 if (receiver is KernelClassBuilder) {
426 Builder builder = receiver.findStaticBuilder(name.name);
427 Member getter = builder?.target;
428 Member setter;
429 if (builder == null) {
430 builder = receiver.findStaticBuilder(name.name, isSetter: true);
431 if (builder == null) {
432 return buildThrowNoSuchMethodError(null);
433 }
434 }
435 if (builder.hasProblem) {
436 return helper.buildProblemExpression(builder, name.name)
437 ..fileOffset = charOffset;
438 }
439 if (getter is Field) {
440 if (!getter.isFinal && !getter.isConst) {
441 setter = getter;
442 }
443 } else if (getter is Procedure) {
444 if (getter.isGetter) {
445 builder = receiver.findStaticBuilder(name.name, isSetter: true);
446 if (builder != null && !builder.hasProblem) {
447 setter = builder.target;
448 }
449 }
450 }
451 if (getter == null) {
452 return internalError("no getter for $name");
453 }
454 return new StaticAccessor(helper, charOffset, getter, setter);
455 }
456 return PropertyAccessor.make(helper, charOffset, helper.toValue(receiver),
457 name, null, null, isNullAware);
458 }
459
460 Expression buildNullAwareAssignment(Expression value, DartType type,
461 {bool voidContext: false}) {
462 return internalError("Unhandled");
463 }
464
465 Expression buildCompoundAssignment(Name binaryOperator, Expression value,
466 {bool voidContext: false, Procedure interfaceTarget}) {
467 return internalError("Unhandled");
468 }
469
470 Expression buildPrefixIncrement(Name binaryOperator,
471 {bool voidContext: false, Procedure interfaceTarget}) {
472 return internalError("Unhandled");
473 }
474
475 Expression buildPostfixIncrement(Name binaryOperator,
476 {bool voidContext: false, Procedure interfaceTarget}) {
477 return internalError("Unhandled");
478 }
479
480 Expression doInvocation(int charOffset, Arguments arguments) {
481 return internalError("Unhandled");
482 }
483
484 toString() => "IncompletePropertyAccessor($charOffset, $name)";
485 }
486
487 class IndexAccessor extends kernel.IndexAccessor with BuilderAccessor {
488 final BuilderHelper helper;
489
490 final int charOffset;
491
492 IndexAccessor.internal(this.helper, this.charOffset, Expression receiver,
493 Expression index, Procedure getter, Procedure setter)
494 : super.internal(receiver, index, getter, setter);
495
496 String get plainNameForRead => "[]";
497
498 String get plainNameForWrite => "[]=";
499
500 Expression doInvocation(int charOffset, Arguments arguments) {
501 return buildMethodInvocation(buildSimpleRead(), new Name("call"), arguments,
502 charOffset);
503 }
504
505 toString() => "IndexAccessor()";
506
507 static BuilderAccessor make(BuilderHelper helper, int charOffset,
508 Expression receiver, Expression index, Procedure getter,
509 Procedure setter) {
510 if (receiver is ThisExpression) {
511 return new ThisIndexAccessor(helper, charOffset, index, getter, setter);
512 } else {
513 return new IndexAccessor.internal(helper, charOffset, receiver, index,
514 getter, setter);
515 }
516 }
517 }
518
519 class PropertyAccessor extends kernel.PropertyAccessor with BuilderAccessor {
520 final BuilderHelper helper;
521
522 final int charOffset;
523
524 PropertyAccessor.internal(this.helper, this.charOffset, Expression receiver,
525 Name name, Member getter, Member setter)
526 : super.internal(receiver, name, getter, setter);
527
528 String get plainNameForRead => name.name;
529
530 bool get isThisPropertyAccessor => receiver is ThisExpression;
531
532 Expression doInvocation(int charOffset, Arguments arguments) {
533 return buildMethodInvocation(receiver, name, arguments, charOffset);
534 }
535
536 toString() => "PropertyAccessor()";
537
538 static BuilderAccessor make(BuilderHelper helper, int charOffset,
539 Expression receiver, Name name, Member getter, Member setter,
540 bool isNullAware) {
541 if (receiver is ThisExpression) {
542 return new ThisPropertyAccessor(helper, charOffset, name, getter, setter);
543 } else {
544 return isNullAware
545 ? new NullAwarePropertyAccessor(helper, charOffset, receiver, name,
546 getter, setter, null)
547 : new PropertyAccessor.internal(helper, charOffset, receiver, name,
548 getter, setter);
549 }
550 }
551 }
552
553 class StaticAccessor extends kernel.StaticAccessor with BuilderAccessor {
554 final BuilderHelper helper;
555
556 final int charOffset;
557
558 StaticAccessor(this.helper, this.charOffset, Member readTarget,
559 Member writeTarget)
560 : super(readTarget, writeTarget) {
561 assert(readTarget != null || writeTarget != null);
562 }
563
564 String get plainNameForRead => (readTarget ?? writeTarget).name.name;
565
566 Expression doInvocation(int charOffset, Arguments arguments) {
567 if (readTarget == null || isFieldOrGetter(readTarget)) {
568 return buildMethodInvocation(buildSimpleRead(), new Name("call"),
569 arguments, charOffset);
570 } else {
571 return helper.buildStaticInvocation(readTarget, arguments)
572 ..fileOffset = charOffset;
573 }
574 }
575
576 toString() => "StaticAccessor()";
577 }
578
579 class SuperPropertyAccessor extends kernel.SuperPropertyAccessor
580 with BuilderAccessor {
581 final BuilderHelper helper;
582
583 final int charOffset;
584
585 SuperPropertyAccessor(this.helper, this.charOffset, Name name, Member getter,
586 Member setter)
587 : super(name, getter, setter);
588
589 String get plainNameForRead => name.name;
590
591 Expression doInvocation(int charOffset, Arguments arguments) {
592 if (getter == null || isFieldOrGetter(getter)) {
593 return buildMethodInvocation(buildSimpleRead(), new Name("call"),
594 arguments, charOffset);
595 } else {
596 return new DirectMethodInvocation(new ThisExpression(), getter, arguments)
597 ..fileOffset = charOffset;
598 }
599 }
600
601 toString() => "SuperPropertyAccessor()";
602 }
603
604 class ThisIndexAccessor extends kernel.ThisIndexAccessor with BuilderAccessor {
605 final BuilderHelper helper;
606
607 final int charOffset;
608
609 ThisIndexAccessor(this.helper, this.charOffset, Expression index,
610 Procedure getter, Procedure setter)
611 : super(index, getter, setter);
612
613 String get plainNameForRead => "[]";
614
615 String get plainNameForWrite => "[]=";
616
617 Expression doInvocation(int charOffset, Arguments arguments) {
618 return buildMethodInvocation(buildSimpleRead(), new Name("call"), arguments,
619 charOffset);
620 }
621
622 toString() => "ThisIndexAccessor()";
623 }
624
625 class ThisPropertyAccessor extends kernel.ThisPropertyAccessor
626 with BuilderAccessor {
627 final BuilderHelper helper;
628
629 final int charOffset;
630
631 ThisPropertyAccessor(this.helper, this.charOffset, Name name, Member getter,
632 Member setter)
633 : super(name, getter, setter);
634
635 String get plainNameForRead => name.name;
636
637 bool get isThisPropertyAccessor => true;
638
639 Expression doInvocation(int charOffset, Arguments arguments) {
640 Member interfaceTarget = getter;
641 if (interfaceTarget is Field) {
642 // TODO(ahe): In strong mode we should probably rewrite this to
643 // `this.name.call(arguments)`.
644 interfaceTarget = null;
645 }
646 return buildMethodInvocation(new ThisExpression(), name, arguments,
647 charOffset);
648 }
649
650 toString() => "ThisPropertyAccessor()";
651 }
652
653 class NullAwarePropertyAccessor extends kernel.NullAwarePropertyAccessor
654 with BuilderAccessor {
655 final BuilderHelper helper;
656
657 final int charOffset;
658
659 NullAwarePropertyAccessor(this.helper, this.charOffset, Expression receiver,
660 Name name, Member getter, Member setter, DartType type)
661 : super(receiver, name, getter, setter, type);
662
663 String get plainNameForRead => name.name;
664
665 Expression doInvocation(int charOffset, Arguments arguments) {
666 return internalError("Not implemented yet.");
667 }
668
669 toString() => "NullAwarePropertyAccessor()";
670 }
671
672
673 class VariableAccessor extends kernel.VariableAccessor
674 with BuilderAccessor {
675 final BuilderHelper helper;
676
677 final int charOffset;
678
679 VariableAccessor(this.helper, this.charOffset, VariableDeclaration variable,
680 [DartType promotedType])
681 : super.internal(variable, promotedType);
682
683 String get plainNameForRead => variable.name;
684
685 Expression doInvocation(int charOffset, Arguments arguments) {
686 return buildMethodInvocation(buildSimpleRead(), new Name("call"), arguments,
687 charOffset);
688 }
689
690 toString() => "VariableAccessor()";
691 }
692
693 Expression throwNoSuchMethodError(String name, Arguments arguments, Uri uri,
694 int charOffset, CoreTypes coreTypes,
695 {bool isSuper: false, isGetter: false, isSetter: false}) {
696 print("$uri:$charOffset: method not found: '$name'.");
697 Constructor constructor = coreTypes.getCoreClass(
698 "dart:core", "NoSuchMethodError").constructors.first;
699 return new Throw(new ConstructorInvocation(
700 constructor,
701 new Arguments(<Expression>[
702 new NullLiteral(),
703 new SymbolLiteral(name),
704 new ListLiteral(arguments.positional),
705 new MapLiteral(arguments.named.map((arg) {
706 return new MapEntry(new SymbolLiteral(arg.name), arg.value);
707 }).toList()),
708 new NullLiteral()])));
709 }
710
711 bool isFieldOrGetter(Member member) {
712 return member is Field || (member is Procedure && member.isGetter);
713 }
714
715 Expression buildMethodInvocation(Expression receiver, Name name,
716 Arguments arguments, int charOffset, {bool isNullAware: false}) {
717 if (isNullAware) {
718 VariableDeclaration variable = new VariableDeclaration.forValue(receiver);
719 return makeLet(
720 variable,
721 new ConditionalExpression(
722 buildIsNull(new VariableGet(variable)),
723 new NullLiteral(),
724 new MethodInvocation(new VariableGet(variable), name, arguments)
725 ..fileOffset = charOffset,
726 const DynamicType()));
727 } else {
728 return new MethodInvocation(receiver, name, arguments)
729 ..fileOffset = charOffset;
730 }
731 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698