| // Copyright (c) 2019, the Dart project authors. Please see the AUTHORS file |
| // for details. All rights reserved. Use of this source code is governed by a |
| // BSD-style license that can be found in the LICENSE file. |
| |
| import 'dart:io'; |
| |
| import 'package:_fe_analyzer_shared/src/messages/severity.dart'; |
| import 'package:expect/expect.dart' show Expect; |
| import 'package:front_end/src/api_prototype/compiler_options.dart'; |
| import 'package:front_end/src/api_prototype/standard_file_system.dart'; |
| import 'package:front_end/src/base/compiler_context.dart'; |
| import 'package:front_end/src/base/file_system_dependency_tracker.dart'; |
| import 'package:front_end/src/base/processed_options.dart'; |
| import 'package:front_end/src/base/ticker.dart'; |
| import 'package:front_end/src/base/uri_translator.dart'; |
| import 'package:front_end/src/compute_platform_binaries_location.dart' |
| show computePlatformBinariesLocation; |
| import 'package:front_end/src/dill/dill_target.dart'; |
| import 'package:front_end/src/kernel/kernel_target.dart'; |
| import 'package:kernel/kernel.dart'; |
| import 'package:kernel/target/targets.dart'; |
| import 'package:vm/modular/target/vm.dart' show VmTarget; |
| |
| import 'utils/io_utils.dart' show computeRepoDirUri; |
| |
| final Uri repoDir = computeRepoDirUri(); |
| |
| Set<String> allowlistedExternalDartFiles = { |
| "third_party/pkg/package_config/lib/package_config.dart", |
| "third_party/pkg/package_config/lib/package_config_types.dart", |
| "third_party/pkg/package_config/lib/src/discovery.dart", |
| "third_party/pkg/package_config/lib/src/errors.dart", |
| "third_party/pkg/package_config/lib/src/package_config_impl.dart", |
| "third_party/pkg/package_config/lib/src/package_config_io.dart", |
| "third_party/pkg/package_config/lib/src/package_config_json.dart", |
| "third_party/pkg/package_config/lib/src/package_config.dart", |
| "third_party/pkg/package_config/lib/src/packages_file.dart", |
| "third_party/pkg/package_config/lib/src/util.dart", |
| |
| // TODO(johnniwinther): Fix to allow dependency of package:package_config. |
| "third_party/pkg/package_config/lib/src/util_io.dart", |
| |
| // TODO(CFE-team): These files should not be included. |
| // The package isn't even in pubspec.yaml. |
| "pkg/meta/lib/meta.dart", |
| "pkg/meta/lib/meta_meta.dart", |
| }; |
| |
| /// Returns true on no errors and false if errors was found. |
| Future<bool> main() async { |
| Ticker ticker = new Ticker(isVerbose: false); |
| CompilerOptions compilerOptions = getOptions(); |
| |
| Uri packageConfigUri = repoDir.resolve(".dart_tool/package_config.json"); |
| if (!new File.fromUri(packageConfigUri).existsSync()) { |
| throw "Couldn't find .dart_tool/package_config.json"; |
| } |
| compilerOptions.packagesFileUri = packageConfigUri; |
| FileSystemDependencyTracker tracker = new FileSystemDependencyTracker(); |
| compilerOptions.fileSystem = StandardFileSystem.instanceWithTracking(tracker); |
| |
| ProcessedOptions options = new ProcessedOptions(options: compilerOptions); |
| |
| Uri frontendLibUri = repoDir.resolve("pkg/front_end/lib/"); |
| List<FileSystemEntity> entities = |
| new Directory.fromUri(frontendLibUri).listSync(recursive: true); |
| for (FileSystemEntity entity in entities) { |
| if (entity is File && entity.path.endsWith(".dart")) { |
| options.inputs.add(entity.uri); |
| } |
| } |
| |
| List<Uri> result = await CompilerContext.runWithOptions<List<Uri>>(options, |
| (CompilerContext c) async { |
| UriTranslator uriTranslator = await c.options.getUriTranslator(); |
| DillTarget dillTarget = |
| new DillTarget(c, ticker, uriTranslator, c.options.target); |
| KernelTarget kernelTarget = |
| new KernelTarget(c, c.fileSystem, false, dillTarget, uriTranslator); |
| Uri? platform = c.options.sdkSummary; |
| if (platform != null) { |
| var bytes = new File.fromUri(platform).readAsBytesSync(); |
| var platformComponent = loadComponentFromBytes(bytes); |
| dillTarget.loader |
| .appendLibraries(platformComponent, byteCount: bytes.length); |
| } |
| |
| kernelTarget.setEntryPoints(c.options.inputs); |
| dillTarget.buildOutlines(); |
| await kernelTarget.loader.buildOutlines(); |
| return new List<Uri>.from(tracker.dependencies); |
| }); |
| |
| Set<Uri> otherDartUris = new Set<Uri>(); |
| Set<Uri> otherNonDartUris = new Set<Uri>(); |
| Set<Uri> frontEndUris = new Set<Uri>(); |
| Set<Uri> kernelUris = new Set<Uri>(); |
| Set<Uri> vmModularUris = new Set<Uri>(); |
| Set<Uri> feAnalyzerSharedUris = new Set<Uri>(); |
| Set<Uri> dartPlatformUris = new Set<Uri>(); |
| Set<Uri> macrosUris = new Set<Uri>(); |
| Uri kernelUri = repoDir.resolve("pkg/kernel/"); |
| Uri vmModularUri = repoDir.resolve("pkg/vm/lib/modular/"); |
| Uri feAnalyzerSharedUri = repoDir.resolve("pkg/_fe_analyzer_shared/"); |
| Uri platformUri1 = repoDir.resolve("sdk/lib/"); |
| Uri platformUri2 = repoDir.resolve("runtime/lib/"); |
| Uri platformUri3 = repoDir.resolve("runtime/bin/"); |
| Uri macrosUri = repoDir.resolve("pkg/macros"); |
| Uri _macrosUri = repoDir.resolve("pkg/_macros"); |
| for (Uri uri in result) { |
| if (uri.toString().startsWith(frontendLibUri.toString())) { |
| frontEndUris.add(uri); |
| } else if (uri.toString().startsWith(kernelUri.toString())) { |
| kernelUris.add(uri); |
| } else if (uri.toString().startsWith(vmModularUri.toString())) { |
| // For VmTarget for macros. |
| vmModularUris.add(uri); |
| } else if (uri.toString().startsWith(feAnalyzerSharedUri.toString())) { |
| feAnalyzerSharedUris.add(uri); |
| } else if (uri.toString().startsWith(platformUri1.toString()) || |
| uri.toString().startsWith(platformUri2.toString()) || |
| uri.toString().startsWith(platformUri3.toString())) { |
| dartPlatformUris.add(uri); |
| } else if (uri.toString().startsWith(_macrosUri.toString()) || |
| uri.toString().startsWith(macrosUri.toString())) { |
| macrosUris.add(uri); |
| } else if (uri.toString().endsWith(".dart")) { |
| otherDartUris.add(uri); |
| } else { |
| otherNonDartUris.add(uri); |
| } |
| } |
| |
| // * Everything in frontEndUris is okay --- the frontend can import itself. |
| // * Everything in kernel is okay --- the frontend is allowed to |
| // import package:kernel. |
| // * Everything in vm/modular is okay, it's specifically for the CFE. |
| // * For other entries, remove allowlisted entries. |
| // * Everything else is an error. |
| |
| // Remove white-listed non-dart files. |
| otherNonDartUris.remove(packageConfigUri); |
| otherNonDartUris.remove(repoDir.resolve("sdk/lib/libraries.json")); |
| otherNonDartUris.remove(repoDir.resolve(".dart_tool/package_config.json")); |
| |
| // Remove white-listed dart files. |
| for (String s in allowlistedExternalDartFiles) { |
| otherDartUris.remove(repoDir.resolve(s)); |
| } |
| |
| if (otherNonDartUris.isNotEmpty || otherDartUris.isNotEmpty) { |
| print("The following files was imported without being allowlisted:"); |
| for (Uri uri in otherNonDartUris) { |
| print(" - $uri"); |
| } |
| for (Uri uri in otherDartUris) { |
| print(" - $uri"); |
| } |
| exitCode = 1; |
| return false; |
| } |
| return true; |
| } |
| |
| CompilerOptions getOptions() { |
| // Compile sdk because when this is run from a lint it uses the checked-in sdk |
| // and we might not have a suitable compiled platform.dill file. |
| Uri sdkRoot = computePlatformBinariesLocation(forceBuildDir: true); |
| CompilerOptions options = new CompilerOptions() |
| ..sdkRoot = sdkRoot |
| ..compileSdk = true |
| ..target = new VmTarget(new TargetFlags()) |
| ..librariesSpecificationUri = repoDir.resolve("sdk/lib/libraries.json") |
| ..omitPlatform = true |
| ..onDiagnostic = (DiagnosticMessage message) { |
| if (message.severity == Severity.error) { |
| Expect.fail( |
| "Unexpected error: ${message.plainTextFormatted.join('\n')}"); |
| } |
| } |
| ..environmentDefines = const {}; |
| return options; |
| } |