| OLD | NEW |
| 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, 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 library source_file_provider; | 5 library source_file_provider; |
| 6 | 6 |
| 7 import 'dart:async'; | 7 import 'dart:async'; |
| 8 import 'dart:convert'; | 8 import 'dart:convert'; |
| 9 import 'dart:io'; | 9 import 'dart:io'; |
| 10 import 'dart:math' as math; |
| 10 | 11 |
| 11 import '../compiler.dart' as api show Diagnostic; | 12 import '../compiler.dart' as api show Diagnostic, DiagnosticHandler; |
| 12 import 'dart2js.dart' show AbortLeg; | 13 import 'dart2js.dart' show AbortLeg; |
| 13 import 'colors.dart' as colors; | 14 import 'colors.dart' as colors; |
| 14 import 'source_file.dart'; | 15 import 'source_file.dart'; |
| 15 import 'filenames.dart'; | 16 import 'filenames.dart'; |
| 16 import 'util/uri_extras.dart'; | 17 import 'util/uri_extras.dart'; |
| 17 import 'dart:typed_data'; | 18 import 'dart:typed_data'; |
| 18 | 19 |
| 19 List<int> readAll(String filename) { | 20 List<int> readAll(String filename) { |
| 20 var file = (new File(filename)).openSync(); | 21 var file = (new File(filename)).openSync(); |
| 21 var length = file.lengthSync(); | 22 var length = file.lengthSync(); |
| (...skipping 144 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 166 if (fatal && ++fatalCount >= throwOnErrorCount && throwOnError) { | 167 if (fatal && ++fatalCount >= throwOnErrorCount && throwOnError) { |
| 167 isAborting = true; | 168 isAborting = true; |
| 168 throw new AbortLeg(message); | 169 throw new AbortLeg(message); |
| 169 } | 170 } |
| 170 } | 171 } |
| 171 | 172 |
| 172 void call(Uri uri, int begin, int end, String message, api.Diagnostic kind) { | 173 void call(Uri uri, int begin, int end, String message, api.Diagnostic kind) { |
| 173 return diagnosticHandler(uri, begin, end, message, kind); | 174 return diagnosticHandler(uri, begin, end, message, kind); |
| 174 } | 175 } |
| 175 } | 176 } |
| 177 |
| 178 typedef void MessageCallback(String message); |
| 179 |
| 180 class RandomAccessFileOutputProvider { |
| 181 final Uri out; |
| 182 final Uri sourceMapOut; |
| 183 final MessageCallback onInfo; |
| 184 final MessageCallback onFailure; |
| 185 |
| 186 int totalCharactersWritten = 0; |
| 187 List<String> allOutputFiles = new List<String>(); |
| 188 |
| 189 RandomAccessFileOutputProvider(this.out, |
| 190 this.sourceMapOut, |
| 191 {this.onInfo, |
| 192 this.onFailure}); |
| 193 |
| 194 static Uri computePrecompiledUri(Uri out) { |
| 195 String extension = 'precompiled.js'; |
| 196 String outPath = out.path; |
| 197 if (outPath.endsWith('.js')) { |
| 198 outPath = outPath.substring(0, outPath.length - 3); |
| 199 return out.resolve('$outPath.$extension'); |
| 200 } else { |
| 201 return out.resolve(extension); |
| 202 } |
| 203 } |
| 204 |
| 205 EventSink<String> call(String name, String extension) { |
| 206 Uri uri; |
| 207 String sourceMapFileName; |
| 208 bool isPrimaryOutput = false; |
| 209 if (name == '') { |
| 210 if (extension == 'js' || extension == 'dart') { |
| 211 isPrimaryOutput = true; |
| 212 uri = out; |
| 213 sourceMapFileName = |
| 214 sourceMapOut.path.substring(sourceMapOut.path.lastIndexOf('/') + 1); |
| 215 } else if (extension == 'precompiled.js') { |
| 216 uri = computePrecompiledUri(out); |
| 217 onInfo("File ($uri) is compatible with header" |
| 218 " \"Content-Security-Policy: script-src 'self'\""); |
| 219 } else if (extension == 'js.map' || extension == 'dart.map') { |
| 220 uri = sourceMapOut; |
| 221 } else if (extension == 'info.html' || extension == "info.json") { |
| 222 String outName = out.path.substring(out.path.lastIndexOf('/') + 1); |
| 223 uri = out.resolve('$outName.$extension'); |
| 224 } else { |
| 225 onFailure('Unknown extension: $extension'); |
| 226 } |
| 227 } else { |
| 228 uri = out.resolve('$name.$extension'); |
| 229 } |
| 230 |
| 231 if (uri.scheme != 'file') { |
| 232 onFailure('Unhandled scheme ${uri.scheme} in $uri.'); |
| 233 } |
| 234 |
| 235 RandomAccessFile output; |
| 236 try { |
| 237 output = new File(uri.toFilePath()).openSync(mode: FileMode.WRITE); |
| 238 } on FileSystemException catch(e) { |
| 239 onFailure('$e'); |
| 240 } |
| 241 |
| 242 allOutputFiles.add(relativize(currentDirectory, uri, Platform.isWindows)); |
| 243 |
| 244 int charactersWritten = 0; |
| 245 |
| 246 writeStringSync(String data) { |
| 247 // Write the data in chunks of 8kb, otherwise we risk running OOM. |
| 248 int chunkSize = 8*1024; |
| 249 |
| 250 int offset = 0; |
| 251 while (offset < data.length) { |
| 252 output.writeStringSync( |
| 253 data.substring(offset, math.min(offset + chunkSize, data.length))); |
| 254 offset += chunkSize; |
| 255 } |
| 256 charactersWritten += data.length; |
| 257 } |
| 258 |
| 259 onDone() { |
| 260 output.closeSync(); |
| 261 if (isPrimaryOutput) { |
| 262 totalCharactersWritten += charactersWritten; |
| 263 } |
| 264 } |
| 265 |
| 266 return new EventSinkWrapper(writeStringSync, onDone); |
| 267 } |
| 268 } |
| 269 |
| 270 class EventSinkWrapper extends EventSink<String> { |
| 271 var onAdd, onClose; |
| 272 |
| 273 EventSinkWrapper(this.onAdd, this.onClose); |
| 274 |
| 275 void add(String data) => onAdd(data); |
| 276 |
| 277 void addError(error, [StackTrace stackTrace]) => throw error; |
| 278 |
| 279 void close() => onClose(); |
| 280 } |
| OLD | NEW |