Chromium Code Reviews| Index: pkg/front_end/lib/src/base/processed_options.dart |
| diff --git a/pkg/front_end/lib/src/base/processed_options.dart b/pkg/front_end/lib/src/base/processed_options.dart |
| index e2cf32a4974c2941b2a07232370cbc4f45a67546..5583b3a9f8dd4f947e8f39edf73019109466e5f0 100644 |
| --- a/pkg/front_end/lib/src/base/processed_options.dart |
| +++ b/pkg/front_end/lib/src/base/processed_options.dart |
| @@ -4,15 +4,16 @@ |
| import 'dart:async'; |
| -import 'package:front_end/compilation_error.dart'; |
| +import 'package:front_end/compilation_message.dart'; |
| import 'package:front_end/compiler_options.dart'; |
| import 'package:front_end/file_system.dart'; |
| import 'package:front_end/src/base/performace_logger.dart'; |
| import 'package:front_end/src/fasta/fasta_codes.dart'; |
| +import 'package:front_end/src/fasta/problems.dart' show unimplemented; |
| +import 'package:front_end/src/fasta/severity.dart'; |
| import 'package:front_end/src/fasta/ticker.dart'; |
| import 'package:front_end/src/fasta/uri_translator.dart'; |
| import 'package:front_end/src/fasta/uri_translator_impl.dart'; |
| -import 'package:front_end/src/fasta/problems.dart' show unimplemented; |
| import 'package:front_end/src/incremental/byte_store.dart'; |
| import 'package:front_end/src/multi_root_file_system.dart'; |
| import 'package:kernel/kernel.dart' |
| @@ -24,6 +25,8 @@ import 'package:package_config/src/packages_impl.dart' |
| show NonFilePackagesDirectoryPackages, MapPackages; |
| import 'package:package_config/packages_file.dart' as package_config; |
| import 'package:source_span/source_span.dart' show SourceSpan, SourceLocation; |
| +import 'package:front_end/src/fasta/command_line_reporting.dart' |
| + as command_line_reporting; |
| /// All options needed for the front end implementation. |
| /// |
| @@ -88,6 +91,14 @@ class ProcessedOptions { |
| bool get setExitCodeOnProblem => _raw.setExitCodeOnProblem; |
| + bool get excludeSourceInformation => _raw.excludeSourceInformation; |
| + |
| + bool get errorsAreFatal => _raw.errorsAreFatal; |
| + |
| + bool get warningsAreFatal => _raw.warningsAreFatal; |
| + |
| + bool get nitsAreFatal => _raw.nitsAreFatal; |
| + |
| /// Like [CompilerOptions.chaseDependencies] but with the appropriate default |
| /// value filled in. |
| bool get chaseDependencies => _raw.chaseDependencies ?? !_modularApi; |
| @@ -100,9 +111,12 @@ class ProcessedOptions { |
| /// The entry-points provided to the compiler. |
| final List<Uri> inputs; |
| + /// The Uri where output is generated, may be null. |
| + final Uri output; |
| + |
| /// Initializes a [ProcessedOptions] object wrapping the given [rawOptions]. |
| ProcessedOptions(CompilerOptions rawOptions, |
| - [this._modularApi = false, this.inputs = const []]) |
| + [this._modularApi = false, this.inputs = const [], this.output]) |
| : this._raw = rawOptions, |
| ticker = new Ticker(isVerbose: rawOptions.verbose); |
| @@ -116,18 +130,34 @@ class ProcessedOptions { |
| return _raw.byteStore; |
| } |
| - void reportMessage(LocatedMessage message) { |
| - _raw.onError(new _CompilationMessage(message)); |
| + bool get _reportMessages => _raw.reportMessages ?? (_raw.onError == null); |
| + |
| + void report(LocatedMessage message, Severity severity) { |
| + if (_raw.onError != null) { |
| + _raw.onError(new _CompilationMessage(message, severity)); |
| + } |
| + |
| + if (_reportMessages) command_line_reporting.report(message, severity); |
| } |
| - void reportMessageWithoutLocation(Message message) => |
| - reportMessage(message.withLocation(null, -1)); |
| + void reportWithoutLocation(Message message, Severity severity) { |
| + if (_raw.onError != null) { |
| + _raw.onError( |
| + new _CompilationMessage(message.withLocation(null, -1), severity)); |
| + } |
| + |
| + if (_reportMessages) { |
| + command_line_reporting.reportWithoutLocation(message, severity); |
| + } |
| + } |
| /// Runs various validations checks on the input options. For instance, |
| /// if an option is a path to a file, it checks that the file exists. |
| Future<bool> validateOptions() async { |
| + if (verbose) print(debugString()); |
| + |
| if (inputs.isEmpty) { |
| - reportMessageWithoutLocation(messageMissingInput); |
| + reportWithoutLocation(messageMissingInput, Severity.error); |
| return false; |
| } |
| @@ -140,30 +170,31 @@ class ProcessedOptions { |
| if (source.scheme != 'dart' && |
| source.scheme != 'packages' && |
| !await fileSystem.entityForUri(source).exists()) { |
| - reportMessageWithoutLocation( |
| - templateInputFileNotFound.withArguments('$source')); |
| + reportWithoutLocation( |
| + templateInputFileNotFound.withArguments('$source'), Severity.error); |
| return false; |
| } |
| } |
| if (_raw.sdkRoot != null && |
| !await fileSystem.entityForUri(sdkRoot).exists()) { |
| - reportMessageWithoutLocation( |
| - templateSdkRootNotFound.withArguments('$sdkRoot')); |
| + reportWithoutLocation( |
| + templateSdkRootNotFound.withArguments('$sdkRoot'), Severity.error); |
| return false; |
| } |
| var summary = sdkSummary; |
| if (summary != null && !await fileSystem.entityForUri(summary).exists()) { |
| - reportMessageWithoutLocation( |
| - templateSdkSummaryNotFound.withArguments('$summary')); |
| + reportWithoutLocation( |
| + templateSdkSummaryNotFound.withArguments('$summary'), Severity.error); |
| return false; |
| } |
| if (compileSdk && summary != null) { |
| - reportMessageWithoutLocation( |
| + reportWithoutLocation( |
| templateInternalProblemUnsupported.withArguments( |
| - "The compileSdk and sdkSummary options are mutually exclusive")); |
| + "The compileSdk and sdkSummary options are mutually exclusive"), |
| + Severity.internalProblem); |
| return false; |
| } |
| return true; |
| @@ -263,21 +294,31 @@ class ProcessedOptions { |
| /// This is an asynchronous getter since file system operations may be |
| /// required to locate/read the packages file. |
| Future<Packages> _getPackages() async { |
| - if (_packages == null) { |
| - if (_raw.packagesFileUri == null) { |
| - if (inputs.length > 1) { |
| - // TODO(sigmund): consider not reporting an error if we would infer |
| - // the same .packages file from all of the inputs. |
| - reportMessageWithoutLocation(messageCantInferPackagesFromManyInputs); |
| - _packages = Packages.noPackages; |
| - } else { |
| - _packages = await _findPackages(inputs.first); |
| - } |
| - } else { |
| - _packages = await createPackagesFromFile(_raw.packagesFileUri); |
| - } |
| + if (_packages != null) return _packages; |
| + if (_raw.packagesFileUri != null) { |
| + return _packages = await createPackagesFromFile(_raw.packagesFileUri); |
| + } |
| + |
| + if (inputs.length > 1) { |
| + // TODO(sigmund): consider not reporting an error if we would infer |
| + // the same .packages file from all of the inputs. |
| + reportWithoutLocation( |
| + messageCantInferPackagesFromManyInputs, Severity.error); |
| + return _packages = Packages.noPackages; |
| + } |
| + |
| + var input = inputs.first; |
| + |
| + // When compiling the SDK the input files are normaly `dart:` URIs. |
|
Siggi Cherem (dart-lang)
2017/07/18 00:11:07
*FYI this is new logic (handling more error cases)
|
| + if (input.scheme == 'dart') return _packages = Packages.noPackages; |
| + |
| + if (input.scheme == 'packages') { |
| + report(messageCantInferPackagesFromPackageUri.withLocation(input, -1), |
| + Severity.error); |
| + return _packages = Packages.noPackages; |
| } |
| - return _packages; |
| + |
| + return _packages = await _findPackages(inputs.first); |
| } |
| /// Create a [Packages] given the Uri to a `.packages` file. |
| @@ -287,9 +328,11 @@ class ProcessedOptions { |
| Map<String, Uri> map = package_config.parse(contents, file); |
| return new MapPackages(map); |
| } catch (e) { |
| - reportMessage(templateCannotReadPackagesFile |
| - .withArguments("$e") |
| - .withLocation(file, -1)); |
| + report( |
| + templateCannotReadPackagesFile |
| + .withArguments("$e") |
| + .withLocation(file, -1), |
| + Severity.error); |
| return Packages.noPackages; |
| } |
| } |
| @@ -318,8 +361,10 @@ class ProcessedOptions { |
| Future<Packages> _findPackages(Uri scriptUri) async { |
| var dir = scriptUri.resolve('.'); |
| if (!dir.isAbsolute) { |
| - reportMessageWithoutLocation(templateInternalProblemUnsupported |
| - .withArguments("Expected input Uri to be absolute: $scriptUri.")); |
| + reportWithoutLocation( |
| + templateInternalProblemUnsupported |
| + .withArguments("Expected input Uri to be absolute: $scriptUri."), |
| + Severity.internalProblem); |
| return Packages.noPackages; |
| } |
| @@ -413,6 +458,56 @@ class ProcessedOptions { |
| } |
| return result; |
| } |
| + |
| + String debugString() { |
|
ahe
2017/07/18 16:54:36
Nice.
|
| + var sb = new StringBuffer(); |
| + writeList(String name, List elements) { |
| + if (elements.isEmpty) { |
| + sb.writeln('$name: <empty>'); |
| + return; |
| + } |
| + sb.writeln('$name:'); |
| + elements.forEach((s) { |
| + sb.writeln(' - $s'); |
| + }); |
| + } |
| + |
| + sb.writeln('Inputs: ${inputs}'); |
| + sb.writeln('Output: ${output}'); |
| + |
| + sb.writeln('Was error handler provided: ' |
| + '${_raw.onError == null ? "no" : "yes"}'); |
| + |
| + sb.writeln('FileSystem: ${_fileSystem.runtimeType} ' |
| + '(provided: ${_raw.fileSystem.runtimeType})'); |
| + |
| + writeList('Input Summaries', _raw.inputSummaries); |
| + writeList('Linked Dependencies', _raw.linkedDependencies); |
| + writeList('Multiroots', _raw.multiRoots); |
| + |
| + sb.writeln('Modular: ${_modularApi}'); |
| + sb.writeln('Hermetic: ${!chaseDependencies}' |
| + ' (provided: ${!_raw.chaseDependencies})'); |
| + sb.writeln('Packages uri: ${_raw.packagesFileUri}'); |
| + sb.writeln('Packages: ${_packages}'); |
| + |
| + sb.writeln('Compile SDK: ${compileSdk}'); |
| + sb.writeln('SDK root: ${_sdkRoot} (provided: ${_raw.sdkRoot})'); |
| + sb.writeln('SDK summary: ${_sdkSummary} (provided: ${_raw.sdkSummary})'); |
| + |
| + sb.writeln('Strong: ${strongMode}'); |
| + sb.writeln('Target: ${_target?.name} (provided: ${_raw.target?.name})'); |
| + |
| + sb.writeln('errorsAreFatal: ${errorsAreFatal}'); |
| + sb.writeln('warningsAreFatal: ${warningsAreFatal}'); |
| + sb.writeln('nitsAreFatal: ${nitsAreFatal}'); |
| + sb.writeln('exit on problem: ${setExitCodeOnProblem}'); |
| + sb.writeln('Exclude sources: ${excludeSourceInformation}'); |
| + sb.writeln('debugDump: ${debugDump}'); |
| + sb.writeln('verbose: ${verbose}'); |
| + sb.writeln('verify: ${verify}'); |
| + return '$sb'; |
| + } |
| } |
| /// A [FileSystem] that only allows access to files that have been explicitly |
| @@ -441,19 +536,24 @@ class HermeticAccessException extends FileSystemException { |
| String toString() => message; |
| } |
| -/// Wraps a [LocatedMessage] to implement the public [CompilationError] API. |
| -class _CompilationMessage implements CompilationError { |
| - final LocatedMessage original; |
| +/// Wraps a [LocatedMessage] to implement the public [CompilationMessage] API. |
| +class _CompilationMessage implements CompilationMessage { |
|
ahe
2017/07/18 16:54:37
You may be able to merge this class with Compilati
Siggi Cherem (dart-lang)
2017/07/18 22:50:43
I have a slight preference to keep them separate b
|
| + final LocatedMessage _original; |
| + final Severity severity; |
| + |
| + String get message => _original.message; |
| + |
| + String get tip => _original.tip; |
| - String get message => original.message; |
| + String get analyzerCode => _original.code.analyzerCode; |
| - String get tip => original.tip; |
| + String get dart2jsCode => _original.code.dart2jsCode; |
| SourceSpan get span => |
| - new SourceLocation(original.charOffset, sourceUrl: original.uri) |
| + new SourceLocation(_original.charOffset, sourceUrl: _original.uri) |
| .pointSpan(); |
| - _CompilationMessage(this.original); |
| + _CompilationMessage(this._original, this.severity); |
| String toString() => message; |
| } |