| OLD | NEW |
| (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.md file. | |
| 4 | |
| 5 library test.kernel.closures.suite; | |
| 6 | |
| 7 import 'dart:async' show Future; | |
| 8 | |
| 9 import 'dart:io' show Directory, File, IOSink; | |
| 10 | |
| 11 import 'dart:typed_data' show Uint8List; | |
| 12 | |
| 13 import 'package:kernel/kernel.dart' show loadProgramFromBinary; | |
| 14 | |
| 15 import 'package:kernel/text/ast_to_text.dart' show Printer; | |
| 16 | |
| 17 import 'package:testing/testing.dart' | |
| 18 show ChainContext, Result, StdioProcess, Step; | |
| 19 | |
| 20 import 'package:kernel/ast.dart' show Library, Program; | |
| 21 | |
| 22 import 'package:kernel/verifier.dart' show verifyProgram; | |
| 23 | |
| 24 import 'package:kernel/binary/ast_to_binary.dart' show BinaryPrinter; | |
| 25 | |
| 26 import 'package:kernel/binary/ast_from_binary.dart' show BinaryBuilder; | |
| 27 | |
| 28 Future<bool> fileExists(Uri base, String path) async { | |
| 29 return await new File.fromUri(base.resolve(path)).exists(); | |
| 30 } | |
| 31 | |
| 32 class Print extends Step<Program, Program, ChainContext> { | |
| 33 const Print(); | |
| 34 | |
| 35 String get name => "print"; | |
| 36 | |
| 37 Future<Result<Program>> run(Program program, _) async { | |
| 38 StringBuffer sb = new StringBuffer(); | |
| 39 for (Library library in program.libraries) { | |
| 40 Printer printer = new Printer(sb); | |
| 41 if (library.importUri.scheme != "dart") { | |
| 42 printer.writeLibraryFile(library); | |
| 43 } | |
| 44 } | |
| 45 print("$sb"); | |
| 46 return pass(program); | |
| 47 } | |
| 48 } | |
| 49 | |
| 50 class SanityCheck extends Step<Program, Program, ChainContext> { | |
| 51 const SanityCheck(); | |
| 52 | |
| 53 String get name => "sanity check"; | |
| 54 | |
| 55 Future<Result<Program>> run(Program program, _) async { | |
| 56 try { | |
| 57 verifyProgram(program); | |
| 58 return pass(program); | |
| 59 } catch (e, s) { | |
| 60 return crash(e, s); | |
| 61 } | |
| 62 } | |
| 63 } | |
| 64 | |
| 65 class MatchExpectation extends Step<Program, Program, ChainContext> { | |
| 66 final String suffix; | |
| 67 | |
| 68 final bool updateExpectations; | |
| 69 | |
| 70 const MatchExpectation(this.suffix, {this.updateExpectations: true}); | |
| 71 | |
| 72 String get name => "match expectations"; | |
| 73 | |
| 74 Future<Result<Program>> run(Program program, _) async { | |
| 75 Library library = program.libraries | |
| 76 .firstWhere((Library library) => library.importUri.scheme != "dart"); | |
| 77 Uri uri = library.importUri; | |
| 78 StringBuffer buffer = new StringBuffer(); | |
| 79 new Printer(buffer).writeLibraryFile(library); | |
| 80 | |
| 81 File expectedFile = new File("${uri.toFilePath()}$suffix"); | |
| 82 if (await expectedFile.exists()) { | |
| 83 String expected = await expectedFile.readAsString(); | |
| 84 if (expected.trim() != "$buffer".trim()) { | |
| 85 if (!updateExpectations) { | |
| 86 String diff = await runDiff(expectedFile.uri, "$buffer"); | |
| 87 return fail(null, "$uri doesn't match ${expectedFile.uri}\n$diff"); | |
| 88 } | |
| 89 } else { | |
| 90 return pass(program); | |
| 91 } | |
| 92 } | |
| 93 if (updateExpectations) { | |
| 94 await openWrite(expectedFile.uri, (IOSink sink) { | |
| 95 sink.writeln("$buffer".trim()); | |
| 96 }); | |
| 97 return pass(program); | |
| 98 } else { | |
| 99 return fail( | |
| 100 program, | |
| 101 """ | |
| 102 Please create file ${expectedFile.path} with this content: | |
| 103 $buffer"""); | |
| 104 } | |
| 105 } | |
| 106 } | |
| 107 | |
| 108 class WriteDill extends Step<Program, Uri, ChainContext> { | |
| 109 const WriteDill(); | |
| 110 | |
| 111 String get name => "write .dill"; | |
| 112 | |
| 113 Future<Result<Uri>> run(Program program, _) async { | |
| 114 Directory tmp = await Directory.systemTemp.createTemp(); | |
| 115 Uri uri = tmp.uri.resolve("generated.dill"); | |
| 116 File generated = new File.fromUri(uri); | |
| 117 IOSink sink = generated.openWrite(); | |
| 118 try { | |
| 119 new BinaryPrinter(sink).writeProgramFile(program); | |
| 120 program.unbindCanonicalNames(); | |
| 121 } catch (e, s) { | |
| 122 return fail(uri, e, s); | |
| 123 } finally { | |
| 124 print("Wrote `${generated.path}`"); | |
| 125 await sink.close(); | |
| 126 } | |
| 127 return pass(uri); | |
| 128 } | |
| 129 } | |
| 130 | |
| 131 class ReadDill extends Step<Uri, Uri, ChainContext> { | |
| 132 const ReadDill(); | |
| 133 | |
| 134 String get name => "read .dill"; | |
| 135 | |
| 136 Future<Result<Uri>> run(Uri uri, _) async { | |
| 137 try { | |
| 138 loadProgramFromBinary(uri.toFilePath()); | |
| 139 } catch (e, s) { | |
| 140 return fail(uri, e, s); | |
| 141 } | |
| 142 return pass(uri); | |
| 143 } | |
| 144 } | |
| 145 | |
| 146 class Copy extends Step<Program, Program, ChainContext> { | |
| 147 const Copy(); | |
| 148 | |
| 149 String get name => "copy program"; | |
| 150 | |
| 151 Future<Result<Program>> run(Program program, _) async { | |
| 152 BytesCollector sink = new BytesCollector(); | |
| 153 new BinaryPrinter(sink).writeProgramFile(program); | |
| 154 program.unbindCanonicalNames(); | |
| 155 Uint8List bytes = sink.collect(); | |
| 156 var newProgram = new Program(); | |
| 157 new BinaryBuilder(bytes).readProgram(newProgram); | |
| 158 newProgram.unbindCanonicalNames(); | |
| 159 return pass(newProgram); | |
| 160 } | |
| 161 } | |
| 162 | |
| 163 class BytesCollector implements Sink<List<int>> { | |
| 164 final List<List<int>> lists = <List<int>>[]; | |
| 165 | |
| 166 int length = 0; | |
| 167 | |
| 168 void add(List<int> data) { | |
| 169 lists.add(data); | |
| 170 length += data.length; | |
| 171 } | |
| 172 | |
| 173 Uint8List collect() { | |
| 174 Uint8List result = new Uint8List(length); | |
| 175 int offset = 0; | |
| 176 for (List<int> list in lists) { | |
| 177 result.setRange(offset, offset += list.length, list); | |
| 178 } | |
| 179 lists.clear(); | |
| 180 length = 0; | |
| 181 return result; | |
| 182 } | |
| 183 | |
| 184 void close() {} | |
| 185 } | |
| 186 | |
| 187 Future<String> runDiff(Uri expected, String actual) async { | |
| 188 StdioProcess process = await StdioProcess | |
| 189 .run("diff", <String>["-u", expected.toFilePath(), "-"], input: actual); | |
| 190 return process.output; | |
| 191 } | |
| 192 | |
| 193 Future openWrite(Uri uri, f(IOSink sink)) async { | |
| 194 IOSink sink = new File.fromUri(uri).openWrite(); | |
| 195 try { | |
| 196 await f(sink); | |
| 197 } finally { | |
| 198 await sink.close(); | |
| 199 } | |
| 200 print("Wrote $uri"); | |
| 201 } | |
| OLD | NEW |