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

Side by Side Diff: tests/language/function_type/test_generator.dart

Issue 2710973002: Revert "Add support for the new function-type syntax." (Closed)
Patch Set: Created 3 years, 10 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 import 'dart:io';
6
7 // By convention:
8 //
9 // T: generic type of typedef.
10 // A: generic type of returned function.
11 // B: generic type of function.
12 //
13 // Example:
14 // typedef F<T>: Function<A> Function<B>();
15 //
16 // We only use: Function, List, int (and function types).
17 // We import 'dart:core' directly and with prefix 'core'.
18
19 abstract class Printable {
20 /// Builds a descriptive string that can be used as an identifier.
21 ///
22 /// The string is mainly used for disambiguation, and not for its readability.
23 void writeIdentifier(StringBuffer buffer);
24 }
25
26 abstract class TypeLike implements Printable {
27 /// Prints `this` as valid Dart code for a Type.
28 void writeType(StringBuffer buffer);
29
30 /// Whether this instance uses T in some way.
31 bool get usesT;
32 }
33
34 /// Provides a unique integer for every parameter in a function.
35 int parameterNameCounter = 0;
36
37 /// Whether `T` should be replaced with `int`.
38 bool shouldReplaceTWithInt = false;
39
40 class Parameter implements Printable {
41 final TypeLike type;
42 final String name;
43
44 Parameter(this.type, this.name);
45
46 // Type or name can be null.
47 @override
48 writeIdentifier(buffer) {
49 if (type == null) {
50 buffer.write("null");
51 } else {
52 type.writeIdentifier(buffer);
53 }
54 buffer.write("_");
55 buffer.write(name);
56 }
57
58 void writeType(StringBuffer buffer) {
59 assert(type != null || name != null);
60 if (name == null) {
61 type.writeType(buffer);
62 } else if (type == null) {
63 buffer.write(name);
64 } else {
65 type.writeType(buffer);
66 buffer.write(" ");
67 buffer.write(name);
68 }
69 }
70
71 void writeInFunction(StringBuffer buffer) {
72 assert(type != null || name != null);
73 if (name == null) {
74 type.writeType(buffer);
75 buffer.write(" x");
76 buffer.write(parameterNameCounter++);
77 } else if (type == null) {
78 buffer.write(name);
79 } else {
80 type.writeType(buffer);
81 buffer.write(" ");
82 buffer.write(name);
83 }
84 }
85
86 bool operator ==(other) {
87 return other is Parameter && name == other.name && type == other.type;
88 }
89
90 int get hashCode {
91 return ((name.hashCode * 37) ^ type.hashCode) & 0xFFFFFFFF;
92 }
93
94 bool get usesT => type?.usesT == true;
95 }
96
97 class GenericParameter implements TypeLike {
98 final String name;
99 final TypeLike bound;
100
101 GenericParameter(this.name, [this.bound]);
102
103 // Bound may be null.
104 @override
105 writeIdentifier(buffer) {
106 buffer.write(name);
107 buffer.write("_");
108 if (bound == null) {
109 buffer.write("null");
110 } else {
111 bound.writeIdentifier(buffer);
112 }
113 }
114
115 @override
116 writeType(buffer) {
117 buffer.write(name);
118 if (bound != null) {
119 buffer.write(" extends ");
120 bound.writeType(buffer);
121 }
122 }
123
124 bool operator ==(other) {
125 return other is GenericParameter &&
126 name == other.name &&
127 bound == other.bound;
128 }
129
130 int get hashCode {
131 return ((name.hashCode * 23) ^ bound.hashCode) & 0xFFFFFFFF;
132 }
133
134 bool get usesT {
135 return bound?.usesT == true;
136 }
137 }
138
139 void _describeList(StringBuffer buffer, List<Printable> list) {
140 if (list == null) {
141 buffer.write("0");
142 return;
143 }
144 buffer.write(list.length.toString());
145 buffer.write("_");
146 for (int i = 0; i < list.length; i++) {
147 if (i != 0) buffer.write("_");
148 list[i].writeIdentifier(buffer);
149 }
150 }
151
152 void _writeTypes(StringBuffer buffer, List<TypeLike> list,
153 [String prefix = "", String postfix = ""]) {
154 if (list == null || list.isEmpty) return;
155 buffer.write(prefix);
156 for (int i = 0; i < list.length; i++) {
157 if (i != 0) buffer.write(", ");
158 list[i].writeType(buffer);
159 }
160 buffer.write(postfix);
161 }
162
163 void _writeParameters(
164 StringBuffer buffer, List<Parameter> list, bool inFunction,
165 [String prefix = "", String postfix = ""]) {
166 if (list == null || list.isEmpty) return;
167 buffer.write(prefix);
168 for (int i = 0; i < list.length; i++) {
169 if (i != 0) buffer.write(", ");
170 if (inFunction) {
171 list[i].writeInFunction(buffer);
172 } else {
173 list[i].writeType(buffer);
174 }
175 }
176 buffer.write(postfix);
177 }
178
179 bool _listUsesT(List elements) {
180 if (elements == null) return false;
181 return elements.any((p) => p.usesT);
182 }
183
184 bool _listEquals(List list1, List list2) {
185 if (list1 == list2) return true; // Also covers both being null.
186 if (list1 == null || list2 == null) return false;
187 for (int i = 0; i < list1.length; i++) {
188 if (list1[i] != list2[i]) return false;
189 }
190 return true;
191 }
192
193 int _listHash(List list) {
194 if (list == null) return null.hashCode;
195 int result = 71;
196 for (int i = 0; i < list.length; i++) {
197 result = ((result * 11) ^ list[i].hashCode) & 0xFFFFFFFF;
198 }
199 return result;
200 }
201
202 class FunctionType implements TypeLike {
203 final TypeLike returnType;
204 final List<GenericParameter> generic;
205 final List<Parameter> required;
206 final List<Parameter> optional;
207 final List<Parameter> named;
208
209 FunctionType(this.returnType, this.generic, this.required,
210 [this.optional, this.named]);
211
212 @override
213 writeIdentifier(buffer) {
214 buffer.write("Fun_");
215 if (returnType == null) {
216 buffer.write("null");
217 } else {
218 returnType.writeIdentifier(buffer);
219 }
220 buffer.write("_");
221 _describeList(buffer, generic);
222 buffer.write("_");
223 _describeList(buffer, required);
224 buffer.write("_");
225 _describeList(buffer, optional);
226 buffer.write("_");
227 _describeList(buffer, named);
228 }
229
230 @override
231 writeType(buffer) {
232 if (returnType != null) {
233 returnType.writeType(buffer);
234 buffer.write(" ");
235 }
236 buffer.write("Function");
237 if (generic != null) _writeTypes(buffer, generic, "<", ">");
238 buffer.write("(");
239 bool notInFunction = true;
240 _writeParameters(buffer, required, notInFunction);
241 if ((optional != null || named != null) &&
242 required != null &&
243 required.isNotEmpty) {
244 buffer.write(", ");
245 }
246 _writeParameters(buffer, optional, notInFunction, "[", "]");
247 _writeParameters(buffer, named, notInFunction, "{", "}");
248 buffer.write(")");
249 }
250
251 /// Writes this type as if it was a function.
252 void writeFunction(StringBuffer buffer, String name, {bool replaceT: true}) {
253 shouldReplaceTWithInt = replaceT;
254 parameterNameCounter = 0;
255
256 if (returnType != null) {
257 returnType.writeType(buffer);
258 buffer.write(" ");
259 }
260
261 buffer.write(name);
262 if (generic != null) _writeTypes(buffer, generic, "<", ">");
263 buffer.write("(");
264 bool inFunction = true;
265 _writeParameters(buffer, required, inFunction);
266 if ((optional != null || named != null) &&
267 required != null &&
268 required.isNotEmpty) {
269 buffer.write(", ");
270 }
271 _writeParameters(buffer, optional, inFunction, "[", "]");
272 _writeParameters(buffer, named, inFunction, "{", "}");
273 buffer.write(") => null;");
274
275 shouldReplaceTWithInt = false;
276 }
277
278 bool operator ==(other) {
279 return returnType == other.returnType &&
280 _listEquals(generic, other.generic) &&
281 _listEquals(required, other.required) &&
282 _listEquals(optional, other.optional) &&
283 _listEquals(named, other.named);
284 }
285
286 int get hashCode {
287 return ((returnType.hashCode * 13) ^
288 (_listHash(generic) * 17) ^
289 (_listHash(required) * 53) ^
290 (_listHash(optional) ^ 31) ^
291 (_listHash(named) * 87)) &
292 0xFFFFFFFF;
293 }
294
295 bool get usesT {
296 return returnType?.usesT == true ||
297 [generic, required, optional, named].any(_listUsesT);
298 }
299 }
300
301 class NominalType implements TypeLike {
302 final String prefix;
303 final String name;
304 final List<TypeLike> generic;
305
306 NominalType(this.name, [this.prefix, this.generic]);
307
308 @override
309 writeIdentifier(buffer) {
310 buffer.write(prefix);
311 buffer.write("_");
312 buffer.write(name);
313 _describeList(buffer, generic);
314 }
315
316 @override
317 writeType(buffer) {
318 if (prefix != null && prefix != "") {
319 buffer.write(prefix);
320 buffer.write(".");
321 }
322 if (shouldReplaceTWithInt && name == "T") {
323 buffer.write("int");
324 } else {
325 buffer.write(name);
326 }
327 _writeTypes(buffer, generic, "<", ">");
328 }
329
330 bool operator ==(other) {
331 return other is NominalType && prefix == other.prefix && name == other.name;
332 }
333
334 int get hashCode {
335 return ((prefix.hashCode * 37) ^ name.hashCode) & 0xFFFFFFFF;
336 }
337
338 bool get usesT => name == "T" || _listUsesT(generic);
339 }
340
341 List<FunctionType> buildFunctionTypes() {
342 List<GenericParameter> as = [
343 new GenericParameter("A"),
344 // new GenericParameter("A", new NominalType("int")),
345 // new GenericParameter("A", new NominalType("int", "core")),
346 ];
347 List<GenericParameter> bs = [
348 // new GenericParameter("B"),
349 // new GenericParameter("B", new NominalType("int")),
350 new GenericParameter("B", new NominalType("int", "core")),
351 ];
352 List<TypeLike> basicTypes = [
353 new NominalType("int"),
354 // new NominalType("int", "core"),
355 // new NominalType("List"),
356 // new NominalType("List", "core"),
357 new NominalType("Function"),
358 new NominalType("List", "", [new NominalType("Function")]),
359 new NominalType("List", "core", [new NominalType("int", "core")]),
360 new NominalType("List", "", [new NominalType("T")]),
361 // new NominalType("List", "", [new NominalType("Function")]),
362 ];
363
364 List<TypeLike> basicsPlusNull = [
365 basicTypes,
366 <TypeLike>[null]
367 ].expand((x) => x).toList();
368
369 List<TypeLike> basicsPlusNullPlusVoid = [
370 basicsPlusNull,
371 [new NominalType("void")],
372 ].expand((x) => x).toList();
373
374 List<TypeLike> basicsPlusNullPlusB = [
375 basicsPlusNull,
376 [
377 new NominalType("B"),
378 new NominalType("List", "", [new NominalType("B")])
379 ]
380 ].expand((x) => x).toList();
381
382 List<TypeLike> basicsPlusNullPlusBPlusVoid = [
383 basicsPlusNullPlusB,
384 [new NominalType("void")],
385 ].expand((x) => x).toList();
386
387 List<TypeLike> basicsPlusNullPlusA = [
388 basicsPlusNull,
389 [
390 new NominalType("A"),
391 new NominalType("List", "", [new NominalType("A")])
392 ]
393 ].expand((x) => x).toList();
394
395 List<TypeLike> basicsPlusNullPlusAPlusVoid = [
396 basicsPlusNullPlusA,
397 [new NominalType("void")],
398 ].expand((x) => x).toList();
399
400 List<TypeLike> buildFunctionTypes(TypeLike returnType, TypeLike parameterType,
401 [List<GenericParameter> generics,
402 bool generateMoreCombinations = false]) {
403 List<TypeLike> result = [];
404
405 if (parameterType == null) {
406 // int Function().
407 result.add(new FunctionType(returnType, generics, null));
408 return result;
409 }
410
411 // int Function(int x).
412 result.add(new FunctionType(
413 returnType, generics, [new Parameter(parameterType, "x")]));
414
415 if (!generateMoreCombinations) return result;
416
417 // int Function([int x]).
418 result.add(new FunctionType(
419 returnType, generics, null, [new Parameter(parameterType, "x")]));
420 // int Function(int, [int x])
421 result.add(new FunctionType(
422 returnType,
423 generics,
424 [new Parameter(new NominalType("int"), null)],
425 [new Parameter(parameterType, "x")]));
426 // int Function(int x, [int x])
427 result.add(new FunctionType(
428 returnType,
429 generics,
430 [new Parameter(new NominalType("int"), "y")],
431 [new Parameter(parameterType, "x")]));
432 // int Function(int);
433 result.add(new FunctionType(
434 returnType, generics, [new Parameter(parameterType, null)]));
435 // int Function([int]);
436 result.add(new FunctionType(
437 returnType, generics, null, [new Parameter(parameterType, null)]));
438 // int Function(int, [int])
439 result.add(new FunctionType(
440 returnType,
441 generics,
442 [new Parameter(new NominalType("int"), null)],
443 [new Parameter(parameterType, null)]));
444 // int Function(int x, [int])
445 result.add(new FunctionType(
446 returnType,
447 generics,
448 [new Parameter(new NominalType("int"), "x")],
449 [new Parameter(parameterType, null)]));
450 // int Function({int x}).
451 result.add(new FunctionType(returnType, generics, null, null,
452 [new Parameter(parameterType, "x")]));
453 // int Function(int, {int x})
454 result.add(new FunctionType(
455 returnType,
456 generics,
457 [new Parameter(new NominalType("int"), null)],
458 null,
459 [new Parameter(parameterType, "x")]));
460 // int Function(int x, {int x})
461 result.add(new FunctionType(
462 returnType,
463 generics,
464 [new Parameter(new NominalType("int"), "y")],
465 null,
466 [new Parameter(parameterType, "x")]));
467 return result;
468 }
469
470 // The "smaller" function types. May also be used non-nested.
471 List<TypeLike> functionTypes = [];
472
473 for (TypeLike returnType in basicsPlusNullPlusVoid) {
474 for (TypeLike parameterType in basicsPlusNull) {
475 bool generateMoreCombinations = true;
476 functionTypes.addAll(buildFunctionTypes(
477 returnType, parameterType, null, generateMoreCombinations));
478 }
479 }
480
481 // These use `B` from the generic type of the enclosing function.
482 List<TypeLike> returnFunctionTypesB = [];
483 for (TypeLike returnType in basicsPlusNullPlusBPlusVoid) {
484 TypeLike parameterType = new NominalType("B");
485 returnFunctionTypesB.addAll(buildFunctionTypes(returnType, parameterType));
486 }
487 for (TypeLike parameterType in basicsPlusNull) {
488 TypeLike returnType = new NominalType("B");
489 returnFunctionTypesB.addAll(buildFunctionTypes(returnType, parameterType));
490 }
491
492 for (TypeLike returnType in basicsPlusNullPlusAPlusVoid) {
493 for (TypeLike parameterType in basicsPlusNullPlusA) {
494 for (GenericParameter a in as) {
495 functionTypes
496 .addAll(buildFunctionTypes(returnType, parameterType, [a]));
497 }
498 }
499 }
500
501 List<TypeLike> types = [];
502 types.addAll(functionTypes);
503
504 // Now add some higher-order function types.
505 for (TypeLike returnType in functionTypes) {
506 types.addAll(buildFunctionTypes(returnType, null));
507 types.addAll(buildFunctionTypes(returnType, new NominalType("int")));
508 for (var b in bs) {
509 types.addAll(buildFunctionTypes(returnType, null, [b]));
510 types.addAll(buildFunctionTypes(returnType, new NominalType("int"), [b]));
511 }
512 }
513 for (TypeLike returnType in returnFunctionTypesB) {
514 for (var b in bs) {
515 types.addAll(buildFunctionTypes(returnType, null, [b]));
516 types.addAll(buildFunctionTypes(returnType, new NominalType("int"), [b]));
517 }
518 }
519
520 return types;
521 }
522
523 final String HEADER = """
524 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file
525 // for details. All rights reserved. Use of this source code is governed by a
526 // BSD-style license that can be found in the LICENSE file.
527
528 // GENERATED - DON'T EDIT.
529 // GENERATED - DON'T EDIT.
530 // GENERATED - DON'T EDIT.
531 // GENERATED - DON'T EDIT.
532 // GENERATED - DON'T EDIT.
533 // GENERATED - DON'T EDIT.
534 // GENERATED - DON'T EDIT.
535 // GENERATED - DON'T EDIT.
536
537 import 'dart:core';
538 import 'dart:core' as core;
539 import 'package:expect/expect.dart';
540
541 @NoInline()
542 @AssumeDynamic()
543 confuse(f) => f;
544
545 final bool inCheckedMode =
546 (() { bool result = false; assert(result = true); return result; })();
547 """;
548
549
550 class Unit {
551 final String name;
552 final StringBuffer typedefs = new StringBuffer();
553 final StringBuffer globals = new StringBuffer();
554 final StringBuffer tests = new StringBuffer();
555 final StringBuffer fields = new StringBuffer();
556 final StringBuffer statics = new StringBuffer();
557 final StringBuffer testMethods = new StringBuffer();
558 final StringBuffer methods = new StringBuffer();
559
560 Unit(this.name);
561
562 void write(StringBuffer buffer) {
563 buffer.write("""
564 $HEADER
565
566 $typedefs
567
568 $globals
569
570 class $name<T> {
571 final bool tIsBool;
572 final bool tIsInt;
573 final bool tIsDynamic;
574
575 $fields
576
577 $name({this.tIsBool: false, this.tIsInt: false})
578 : tIsDynamic = !tIsBool && !tIsInt;
579
580 $methods
581
582 runTests() {\n$tests }
583
584 $testMethods
585 }
586
587 void main() {
588 new $name().runTests();
589 new $name<int>(tIsInt: true).runTests();
590 new $name<bool>(tIsBool: true).runTests();
591 }
592 """);
593 }
594 }
595
596
597 final TEST_METHOD_HEADER = """
598 void #testName() {
599 // #typeCode""";
600
601 // Tests that apply for every type.
602 final COMMON_TESTS_TEMPLATE = """
603 Expect.isTrue(#staticFunName is #typeName);
604 Expect.isTrue(confuse(#staticFunName) is #typeName);
605 // In checked mode, verifies the type.
606 #typeCode #localName;
607 // The static function #staticFunName sets `T` to `int`.
608 if (!tIsBool) {
609 #fieldName = #staticFunName as dynamic;
610 #localName = #staticFunName as dynamic;
611 #fieldName = confuse(#staticFunName);
612 #localName = confuse(#staticFunName);
613 }
614
615 Expect.isTrue(#methodFunName is #typeName);
616 Expect.isTrue(#methodFunName is #typeCode);
617 Expect.isTrue(confuse(#methodFunName) is #typeName);
618 // In checked mode, verifies the type.
619 #fieldName = #methodFunName;
620 #localName = #methodFunName;
621 #fieldName = confuse(#methodFunName);
622 #localName = confuse(#methodFunName);""";
623
624 // Tests that depend on the typedef "T" argument.
625 //
626 // These tests are executed when the surrounding class is instantiated with
627 // its generic type set to `int`, `dynamic` or `bool`. In the latter case, the
628 // class field `tIsBool` is set to true.
629
630 // While the types themselves are not affected by the class` `T`, the methods
631 // of the class may use `T`:
632 //
633 // For example:
634 // class A<T> {
635 // f(List<T> x) {}
636 // }
637 final TYPEDEF_T_TESTS_TEMPLATE = """
638 if (!tIsBool) {
639 Expect.isTrue(#staticFunName is #typeName<int>);
640 Expect.isFalse(#staticFunName is #typeName<bool>);
641 Expect.isTrue(confuse(#staticFunName) is #typeName<int>);
642 Expect.isFalse(confuse(#staticFunName) is #typeName<bool>);
643 Expect.equals(tIsDynamic, #methodFunName is #typeName<bool>);
644 Expect.equals(tIsDynamic, confuse(#methodFunName) is #typeName<bool>);
645 } else {
646 if (inCheckedMode) {
647 Expect.throws(() { #fieldName = (#staticFunName as dynamic); });
648 Expect.throws(() { #fieldName = confuse(#staticFunName); });
649 #typeCode #localName;
650 Expect.throws(() { #localName = (#staticFunName as dynamic); });
651 Expect.throws(() { #localName = confuse(#staticFunName); });
652 }
653 #typeCode #localName = #methodFunName;
654 // In checked mode, verifies the type.
655 #fieldName = #methodFunName;
656 #fieldName = confuse(#methodFunName);
657 }""";
658
659 final TEST_METHOD_FOOTER = " }";
660
661 String createTypeName(int id) => "F$id";
662 String createStaticFunName(int id) => "f$id";
663 String createMethodFunName(int id) => "m$id";
664 String createFieldName(int id) => "x$id";
665 String createLocalName(int id) => "l$id";
666 String createTestName(int id) => "test${createTypeName(id)}";
667
668 String createTypeCode(FunctionType type) {
669 StringBuffer typeBuffer = new StringBuffer();
670 type.writeType(typeBuffer);
671 return typeBuffer.toString();
672 }
673 String createStaticFunCode(FunctionType type, int id) {
674 StringBuffer staticFunBuffer = new StringBuffer();
675 type.writeFunction(staticFunBuffer, createStaticFunName(id));
676 return staticFunBuffer.toString();
677 }
678
679 String createMethodFunCode(FunctionType type, int id) {
680 StringBuffer methodFunBuffer = new StringBuffer();
681 type.writeFunction(methodFunBuffer, createMethodFunName(id), replaceT: false);
682 return methodFunBuffer.toString();
683 }
684
685 String createTestMethodFunCode(FunctionType type, String typeCode, int id) {
686 String fillTemplate(String template, int id) {
687 var result = template
688 .replaceAll("#typeName", createTypeName(id))
689 .replaceAll("#staticFunName", createStaticFunName(id))
690 .replaceAll("#methodFunName", createMethodFunName(id))
691 .replaceAll("#fieldName", createFieldName(id))
692 .replaceAll("#localName", createLocalName(id))
693 .replaceAll("#testName", createTestName(id))
694 .replaceAll("#typeCode", typeCode);
695 assert(!result.contains("#"));
696 return result;
697 }
698
699 String commonTests = fillTemplate(COMMON_TESTS_TEMPLATE, id);
700 String genericTTests = "";
701 if (type.usesT) {
702 genericTTests = fillTemplate(TYPEDEF_T_TESTS_TEMPLATE, id);
703 }
704 return """
705 ${fillTemplate(TEST_METHOD_HEADER, id)}
706 $commonTests
707 $genericTTests
708 $TEST_METHOD_FOOTER
709 """;
710 }
711
712 void generateTests() {
713 // Keep methods and classes smaller by distributing over several different
714 // classes.
715 List<Unit> units = [];
716 for (int i = 0; i < 100; i++) {
717 units.add(new Unit("U$i"));
718 }
719
720 var types = buildFunctionTypes();
721
722 int typeCounter = 0;
723 types.forEach((FunctionType type) {
724 Unit unit = units[typeCounter % units.length];
725
726 String typeName = createTypeName(typeCounter);
727 String fieldName = createFieldName(typeCounter);
728 String testName = createTestName(typeCounter);
729
730 String typeCode = createTypeCode(type);
731 String staticFunCode = createStaticFunCode(type, typeCounter);
732 String methodFunCode = createMethodFunCode(type, typeCounter);
733 String testMethodCode =
734 createTestMethodFunCode(type, typeCode, typeCounter);
735
736
737 unit.typedefs.writeln("typedef $typeName<T> = $typeCode;");
738 unit.globals.writeln(staticFunCode);
739 unit.fields.writeln(" $typeCode $fieldName;");
740 unit.methods.writeln(" $methodFunCode");
741 unit.testMethods.writeln("$testMethodCode");
742 unit.tests.writeln(" $testName();");
743
744 typeCounter++;
745 });
746
747 for (int i = 0; i < units.length; i++) {
748 var unit = units[i];
749 var buffer = new StringBuffer();
750 unit.write(buffer);
751 var path = Platform.script.resolve("function_type${i}_test.dart").path;
752 new File(path).writeAsStringSync(buffer.toString());
753 }
754 }
755
756 void printUsage() {
757 print("""
758 Generates function type tests.
759
760 All tests are generated in the same directory as this script.
761 """);
762 }
763
764 void main(List<String> arguments) {
765 if (arguments.length != 0) {
766 printUsage();
767 return;
768 }
769 generateTests();
770 }
OLDNEW
« no previous file with comments | « tests/compiler/dart2js/resolver_test.dart ('k') | tests/language/generic_function_typedef2_test.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698