Version 2.18.0-228.0.dev
Merge commit 'e7b77987ff4fd03350703bd12264e60f5a805be6' into 'dev'
diff --git a/DEPS b/DEPS
index 9821742..3a4ccc5 100644
--- a/DEPS
+++ b/DEPS
@@ -90,7 +90,7 @@
"characters_rev": "559755d67af2c78b9beaaeb7ca57d7c4ae0b836d",
"chrome_rev": "19997",
"cli_util_rev": "b0adbba89442b2ea6fef39c7a82fe79cb31e1168",
- "clock_rev": "a75eb69c8e939e2e7eab70e4728da3bcf004e717",
+ "clock_rev": "2507a228773c5e877fc9e3330080b234aad965c0",
"collection_rev": "414ffa1bc8ba18bd608bbf916d95715311d89ac1",
"convert_rev": "7145da14f9cd730e80fb4c6a10108fcfd205e8e7",
"crypto_rev": "223e0a62c0f762fd2b510f753861445b52e14fc3",
@@ -113,34 +113,34 @@
"ffi_rev": "18b2b549d55009ff594600b04705ff6161681e07",
"file_rev": "0132eeedea2933513bf230513a766a8baeab0c4f",
"fixnum_rev": "164712f6547cdfb2709b752188186baf31fd1730",
- "glob_rev": "e10eb2407c58427144004458ef85c9bbf7286e56",
+ "glob_rev": "1d51fcc172e5adfbae6e82c3f8f119774cb2fca2",
"html_rev": "8243e967caad9932c13971af3b2a7c8f028383d5",
- "http_multi_server_rev": "35a3b947256768426090e3b1f5132e4fc23c175d",
+ "http_multi_server_rev": "20bf079c8955d1250a45afb9cb096472a724a551",
"http_parser_rev": "eaa63304c333316acd114e3be7ed701d7d7ba32c",
- "http_rev": "0c2293062d7c1fa472f299da764a7dbb3895ee22",
+ "http_rev": "0c2293062d7c1fa472f299da764a7dbb3895ee22", # b/237080804
"icu_rev": "81d656878ec611cb0b42d52c82e9dae93920d9ba",
"intl_rev": "e9b573679de5e703d89a242b9dca331c772979ef",
"jinja2_rev": "2222b31554f03e62600cd7e383376a7c187967a1",
- "json_rpc_2_rev": "2de9a1f9821807fa2c85fd48e2f70b9cbcddcb67",
+ "json_rpc_2_rev": "805e6536dd961d66f6b8cd46d8f3e61774f957c9",
"linter_rev": "1ddc70948d94f2449fec69a95e3ceb7b6b6c8348", # manually rev'd
"lints_rev": "8294e5648ab49474541527e2911e72e4c5aefe55",
"logging_rev": "f6979e3bc3b6e1847a08335b7eb6304e18986195",
"markdown_rev": "e3f4bd28c9e61b522f75f291d4d6cfcfeccd83ee", # b/236358256
"markupsafe_rev": "8f45f5cfa0009d2a70589bcda0349b8cb2b72783",
- "matcher_rev": "12cdc5fbafd666ed908359ae215d5d0306087969",
+ "matcher_rev": "1a7fcae0d7af1604781afabe61fd35d9b404d8ed",
"mime_rev": "0a75a41445eb642674a0a271eecde78cb025ee60",
"mockito_rev": "25d25dab6b57ac710c0be0e759def7505b352ea7",
"oauth2_rev": "199ebf15cbd5b07958438184f32e41c4447a57bf",
"package_config_rev": "cff98c90acc457a3b0750f0a7da0e351a35e5d0c",
"path_rev": "7a0ed40280345b1c11df4c700c71e590738f4257",
"ply_rev": "604b32590ffad5cbb82e4afef1d305512d06ae93",
- "pool_rev": "c40cc32eabecb9d60f1045d1403108d968805f9a",
- "protobuf_rev": "3149f6f2d323e11dbcc983b7ac8b3b9e9d686293",
+ "pool_rev": "fa84ddd0e39f45bf3f09dcc5d6b9fbdda7820fef",
+ "protobuf_rev": "58f49c50f93d190adaec213ad500d7de5fe20b2f",
"pub_rev": "9bf4289d6fd5d6872a8929d6312bbd7098f3ea9c", # manually rev'd
"pub_semver_rev": "5c0b4bfd5ca57fe16f1319c581dc8c882e9b8cb2",
"root_certificates_rev": "692f6d6488af68e0121317a9c2c9eb393eb0ee50",
"rust_revision": "b7856f695d65a8ebc846754f97d15814bcb1c244",
- "shelf_rev": "05f42601d22c9bfe490ceda50e812f83b7d1de77",
+ "shelf_rev": "8f8f3703efd241f9cf6b18e36e0067ca74c47fd8",
"source_map_stack_trace_rev": "72dbf21a33293b2b8434d0a9751e36f9463981ac",
"source_maps_rev": "e93565b43a7b6b367789de8ffba969c4ebeeb317",
"source_span_rev": "24151fd80e4557a626f81f2bc0d6a2ebde172cae",
@@ -149,11 +149,11 @@
"stream_channel_rev": "8e0d7ef1f4a3fb97fbd82e11cd539093f58511f3",
"string_scanner_rev": "c637deb8d998b72a5807afbd06aba8370db725c0",
"sync_http_rev": "39509d69fd5a9c3da46eab48fcafdf62e6ad4580",
- "term_glyph_rev": "d0f205c67ea70eea47b9f41c8440129a72a9c86e",
+ "term_glyph_rev": "741efdedf9da62ee66a06c295d36fa28f8780e24",
"test_descriptor_rev": "5ed5d7f6bf1191592995dcb8eedbbc17df69d386",
"test_process_rev": "3e695bcfeab551473ddc288970f345f30e5e1375",
"test_reflective_loader_rev": "8d0de01bbe852fea1f8e33aba907abcba50a8a1e",
- "test_rev": "90ec2561a9725d54597498d51b23f1ccf09a6db1",
+ "test_rev": "6d656f60f2c486efce5f4f22ff00dbb037a825f1",
"typed_data_rev": "bb10b64f9a56b8fb49307d4465474bf1c1309f6d",
"usage_rev": "1d3c31e780af665fb796a27898a441fcb7d263db",
"vector_math_rev": "cdcee487bde4353a6ba7a29bfc7db3840426e50f",
@@ -161,7 +161,7 @@
"web_components_rev": "8f57dac273412a7172c8ade6f361b407e2e4ed02",
"web_socket_channel_rev": "99dbdc5769e19b9eeaf69449a59079153c6a8b1f",
"WebCore_rev": "bcb10901266c884e7b3740abc597ab95373ab55c",
- "webdev_rev": "a74737fc46286b3e34475e20e6e44fc92efc8916",
+ "webdev_rev": "b0a4059dcdfb3af2a011cbefc5eb21fb0cfd8032",
"webdriver_rev": "e1a9ad671ee82e05eee463f922a34585ed2d2f15",
"webkit_inspection_protocol_rev": "57522d6b29d94903b765c757079d906555d5a171",
"yaml_edit_rev": "01589b3ce447b03aed991db49f1ec6445ad5476d",
diff --git a/pkg/analysis_server/lib/src/services/correction/dart/remove_const.dart b/pkg/analysis_server/lib/src/services/correction/dart/remove_const.dart
index 832dd64e..9d8bb75 100644
--- a/pkg/analysis_server/lib/src/services/correction/dart/remove_const.dart
+++ b/pkg/analysis_server/lib/src/services/correction/dart/remove_const.dart
@@ -6,7 +6,6 @@
import 'package:analysis_server/src/services/correction/fix.dart';
import 'package:analyzer/dart/ast/ast.dart';
import 'package:analyzer/dart/ast/token.dart';
-import 'package:analyzer/src/dart/ast/ast.dart';
import 'package:analyzer_plugin/utilities/change_builder/change_builder_core.dart';
import 'package:analyzer_plugin/utilities/fixes/fixes.dart';
import 'package:analyzer_plugin/utilities/range_factory.dart';
@@ -38,7 +37,7 @@
Token? constToken;
if (expression is InstanceCreationExpression) {
constToken = expression.keyword;
- } else if (expression is TypedLiteralImpl) {
+ } else if (expression is TypedLiteral) {
constToken = expression.constKeyword;
}
diff --git a/pkg/analysis_server/lib/src/services/correction/dart/replace_final_with_const.dart b/pkg/analysis_server/lib/src/services/correction/dart/replace_final_with_const.dart
index ac56fdf..af3a2ce 100644
--- a/pkg/analysis_server/lib/src/services/correction/dart/replace_final_with_const.dart
+++ b/pkg/analysis_server/lib/src/services/correction/dart/replace_final_with_const.dart
@@ -5,6 +5,7 @@
import 'package:analysis_server/src/services/correction/dart/abstract_producer.dart';
import 'package:analysis_server/src/services/correction/fix.dart';
import 'package:analyzer/dart/ast/ast.dart';
+import 'package:analyzer/dart/ast/token.dart';
import 'package:analyzer_plugin/utilities/change_builder/change_builder_core.dart';
import 'package:analyzer_plugin/utilities/fixes/fixes.dart';
import 'package:analyzer_plugin/utilities/range_factory.dart';
@@ -32,6 +33,31 @@
builder.addSimpleReplacement(range.token(keyword), 'const');
});
}
+
+ for (var variable in node.variables) {
+ var initializer = variable.initializer;
+ if (initializer != null) {
+ Token? constToken;
+ if (initializer is InstanceCreationExpression) {
+ constToken = initializer.keyword;
+ } else if (initializer is TypedLiteral) {
+ constToken = initializer.constKeyword;
+ }
+
+ if (constToken == null) {
+ continue;
+ }
+
+ await builder.addDartFileEdit(file, (builder) {
+ builder.addDeletion(
+ range.startStart(
+ constToken!,
+ constToken.next!,
+ ),
+ );
+ });
+ }
+ }
}
}
}
diff --git a/pkg/analysis_server/lib/src/services/correction/error_fix_status.yaml b/pkg/analysis_server/lib/src/services/correction/error_fix_status.yaml
index cba9147..9c87e09 100644
--- a/pkg/analysis_server/lib/src/services/correction/error_fix_status.yaml
+++ b/pkg/analysis_server/lib/src/services/correction/error_fix_status.yaml
@@ -382,9 +382,8 @@
would be more likely that the user needed to restructure the mixin so that
part of it could be included here.
CompileTimeErrorCode.ENUM_WITH_ABSTRACT_MEMBER:
- status: needsFix
+ status: hasFix
since: 2.17
- issue: https://github.com/dart-lang/sdk/issues/48478
CompileTimeErrorCode.ENUM_WITH_NAME_VALUES:
status: noFix
since: 2.17
diff --git a/pkg/analysis_server/lib/src/services/correction/fix_internal.dart b/pkg/analysis_server/lib/src/services/correction/fix_internal.dart
index 61583a8..9e1f5f29 100644
--- a/pkg/analysis_server/lib/src/services/correction/fix_internal.dart
+++ b/pkg/analysis_server/lib/src/services/correction/fix_internal.dart
@@ -908,6 +908,9 @@
ConvertToListLiteral.new,
ReplaceWithFilled.new,
],
+ CompileTimeErrorCode.ENUM_WITH_ABSTRACT_MEMBER: [
+ ConvertIntoBlockBody.new,
+ ],
CompileTimeErrorCode.EXTENDS_NON_CLASS: [
ChangeTo.classOrMixin,
CreateClass.new,
diff --git a/pkg/analysis_server/test/src/services/correction/fix/convert_into_block_body_test.dart b/pkg/analysis_server/test/src/services/correction/fix/convert_into_block_body_test.dart
index 8d2f3e8..a9904be 100644
--- a/pkg/analysis_server/test/src/services/correction/fix/convert_into_block_body_test.dart
+++ b/pkg/analysis_server/test/src/services/correction/fix/convert_into_block_body_test.dart
@@ -19,6 +19,58 @@
@override
FixKind get kind => DartFixKind.CONVERT_INTO_BLOCK_BODY;
+ Future<void> test_enum_getter() async {
+ await resolveTestCode('''
+enum E {
+ v;
+ int get g;
+}
+''');
+ await assertHasFix('''
+enum E {
+ v;
+ int get g {
+ // TODO: implement g
+ throw UnimplementedError();
+ }
+}
+''');
+ }
+
+ Future<void> test_enum_method() async {
+ await resolveTestCode('''
+enum E {
+ v;
+ void m();
+}
+''');
+ await assertHasFix('''
+enum E {
+ v;
+ void m() {
+ // TODO: implement m
+ }
+}
+''');
+ }
+
+ Future<void> test_enum_setter() async {
+ await resolveTestCode('''
+enum E {
+ v;
+ set s(int _);
+}
+''');
+ await assertHasFix('''
+enum E {
+ v;
+ set s(int _) {
+ // TODO: implement s=
+ }
+}
+''');
+ }
+
Future<void> test_function() async {
await resolveTestCode('''
void f();
diff --git a/pkg/analysis_server/test/src/services/correction/fix/replace_final_with_const_test.dart b/pkg/analysis_server/test/src/services/correction/fix/replace_final_with_const_test.dart
index 7cb0d8d..7c3c8dc 100644
--- a/pkg/analysis_server/test/src/services/correction/fix/replace_final_with_const_test.dart
+++ b/pkg/analysis_server/test/src/services/correction/fix/replace_final_with_const_test.dart
@@ -41,7 +41,46 @@
@override
String get lintCode => LintNames.prefer_const_declarations;
- Future<void> test_method() async {
+ Future<void> test_const_instanceCreation() async {
+ await resolveTestCode('''
+class A {
+ const A();
+}
+final a = const A();
+''');
+ await assertHasFix('''
+class A {
+ const A();
+}
+const a = A();
+''');
+ }
+
+ Future<void> test_const_instanceCreation_multiple() async {
+ await resolveTestCode('''
+class A {
+ const A();
+}
+final A a1 = const A(), a2 = const A();
+''');
+ await assertHasFix('''
+class A {
+ const A();
+}
+const A a1 = A(), a2 = A();
+''');
+ }
+
+ Future<void> test_const_typedLiteral() async {
+ await resolveTestCode('''
+final b = const [];
+''');
+ await assertHasFix('''
+const b = [];
+''');
+ }
+
+ Future<void> test_variable() async {
await resolveTestCode('''
final int a = 1;
''');
diff --git a/pkg/analyzer/lib/src/dart/analysis/driver.dart b/pkg/analyzer/lib/src/dart/analysis/driver.dart
index 5f5d2d2..31d2579 100644
--- a/pkg/analyzer/lib/src/dart/analysis/driver.dart
+++ b/pkg/analyzer/lib/src/dart/analysis/driver.dart
@@ -2110,7 +2110,10 @@
class AnalysisDriverTestView {
final fileSystem = FileSystemTestData();
- final libraryContext = LibraryContextTestData();
+
+ late final libraryContext = LibraryContextTestData(
+ fileSystemTestData: fileSystem,
+ );
late final AnalysisDriver driver;
diff --git a/pkg/analyzer/lib/src/dart/analysis/file_state.dart b/pkg/analyzer/lib/src/dart/analysis/file_state.dart
index 4e4f4e6..ab9e741 100644
--- a/pkg/analyzer/lib/src/dart/analysis/file_state.dart
+++ b/pkg/analyzer/lib/src/dart/analysis/file_state.dart
@@ -1476,6 +1476,11 @@
final List<String> unlinkedKeyPut = [];
FileTestData._(this.file, this.uri);
+
+ @override
+ bool operator ==(Object other) {
+ return other is FileTestData && other.file == file && other.uri == uri;
+ }
}
/// Precomputed properties of a file URI, used because [Uri] is relatively
diff --git a/pkg/analyzer/lib/src/dart/analysis/library_context.dart b/pkg/analyzer/lib/src/dart/analysis/library_context.dart
index 8a81e56..c67c6b5 100644
--- a/pkg/analyzer/lib/src/dart/analysis/library_context.dart
+++ b/pkg/analyzer/lib/src/dart/analysis/library_context.dart
@@ -10,7 +10,6 @@
import 'package:analyzer/dart/analysis/declared_variables.dart';
import 'package:analyzer/dart/element/element.dart'
show CompilationUnitElement, LibraryElement;
-import 'package:analyzer/file_system/file_system.dart';
import 'package:analyzer/src/context/context.dart';
import 'package:analyzer/src/dart/analysis/byte_store.dart';
import 'package:analyzer/src/dart/analysis/driver.dart';
@@ -373,18 +372,27 @@
}
class LibraryContextTestData {
+ final FileSystemTestData fileSystemTestData;
+
/// TODO(scheglov) Use [libraryCycles] and textual dumps for the driver too.
final List<Set<String>> linkedCycles = [];
/// Keys: the sorted list of library files.
- final Map<List<File>, LibraryCycleTestData> libraryCycles = LinkedHashMap(
+ final Map<List<FileTestData>, LibraryCycleTestData> libraryCycles =
+ LinkedHashMap(
hashCode: Object.hashAll,
- equals: const ListEquality<File>().equals,
+ equals: const ListEquality<FileTestData>().equals,
);
+ LibraryContextTestData({
+ required this.fileSystemTestData,
+ });
+
LibraryCycleTestData forCycle(LibraryCycle cycle) {
- final files = cycle.libraries.map((e) => e.resource).toList();
- files.sortBy((file) => file.path);
+ final files = cycle.libraries.map((e) {
+ return fileSystemTestData.forFile(e.resource, e.uri);
+ }).toList();
+ files.sortBy((fileData) => fileData.file.path);
return libraryCycles[files] ??= LibraryCycleTestData();
}
diff --git a/pkg/analyzer/lib/src/dart/micro/library_analyzer.dart b/pkg/analyzer/lib/src/dart/micro/library_analyzer.dart
deleted file mode 100644
index f81ea9f..0000000
--- a/pkg/analyzer/lib/src/dart/micro/library_analyzer.dart
+++ /dev/null
@@ -1,857 +0,0 @@
-// Copyright (c) 2020, 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 'package:analyzer/dart/analysis/declared_variables.dart';
-import 'package:analyzer/dart/analysis/features.dart';
-import 'package:analyzer/dart/ast/ast.dart';
-import 'package:analyzer/dart/element/element.dart';
-import 'package:analyzer/error/error.dart';
-import 'package:analyzer/error/listener.dart';
-import 'package:analyzer/src/context/source.dart';
-import 'package:analyzer/src/dart/analysis/file_state.dart';
-import 'package:analyzer/src/dart/ast/ast.dart';
-import 'package:analyzer/src/dart/ast/utilities.dart';
-import 'package:analyzer/src/dart/constant/compute.dart';
-import 'package:analyzer/src/dart/constant/constant_verifier.dart';
-import 'package:analyzer/src/dart/constant/evaluation.dart';
-import 'package:analyzer/src/dart/constant/utilities.dart';
-import 'package:analyzer/src/dart/element/element.dart';
-import 'package:analyzer/src/dart/element/inheritance_manager3.dart';
-import 'package:analyzer/src/dart/element/type_provider.dart';
-import 'package:analyzer/src/dart/element/type_system.dart';
-import 'package:analyzer/src/dart/resolver/flow_analysis_visitor.dart';
-import 'package:analyzer/src/dart/resolver/legacy_type_asserter.dart';
-import 'package:analyzer/src/dart/resolver/resolution_visitor.dart';
-import 'package:analyzer/src/error/best_practices_verifier.dart';
-import 'package:analyzer/src/error/codes.dart';
-import 'package:analyzer/src/error/dead_code_verifier.dart';
-import 'package:analyzer/src/error/ignore_validator.dart';
-import 'package:analyzer/src/error/imports_verifier.dart';
-import 'package:analyzer/src/error/inheritance_override.dart';
-import 'package:analyzer/src/error/override_verifier.dart';
-import 'package:analyzer/src/error/todo_finder.dart';
-import 'package:analyzer/src/error/unicode_text_verifier.dart';
-import 'package:analyzer/src/error/unused_local_elements_verifier.dart';
-import 'package:analyzer/src/generated/element_walker.dart';
-import 'package:analyzer/src/generated/engine.dart';
-import 'package:analyzer/src/generated/error_verifier.dart';
-import 'package:analyzer/src/generated/resolver.dart';
-import 'package:analyzer/src/generated/source.dart';
-import 'package:analyzer/src/hint/sdk_constraint_verifier.dart';
-import 'package:analyzer/src/ignore_comments/ignore_info.dart';
-import 'package:analyzer/src/lint/linter.dart';
-import 'package:analyzer/src/lint/linter_visitor.dart';
-import 'package:analyzer/src/services/lint.dart';
-import 'package:analyzer/src/summary2/linked_element_factory.dart';
-import 'package:analyzer/src/task/strong/checker.dart';
-import 'package:analyzer/src/util/performance/operation_performance.dart';
-import 'package:analyzer/src/workspace/workspace.dart';
-
-/// Analyzer of a single library.
-class LibraryAnalyzer {
- final AnalysisOptionsImpl _analysisOptions;
- final DeclaredVariables _declaredVariables;
- final SourceFactory _sourceFactory;
- final FileState _library;
-
- final InheritanceManager3 _inheritance;
- final bool Function(Uri) _isLibraryUri;
- final AnalysisContext _context;
- final LinkedElementFactory _elementFactory;
-
- late LibraryElementImpl _libraryElement;
-
- final Map<FileState, LineInfo> _fileToLineInfo = {};
-
- final Map<FileState, IgnoreInfo> _fileToIgnoreInfo = {};
- final Map<FileState, RecordingErrorListener> _errorListeners = {};
- final Map<FileState, ErrorReporter> _errorReporters = {};
- final List<UsedImportedElements> _usedImportedElementsList = [];
- final List<UsedLocalElements> _usedLocalElementsList = [];
-
- /// Constants in the current library.
- ///
- /// TODO(scheglov) Remove after https://github.com/dart-lang/sdk/issues/31925
- final Set<ConstantEvaluationTarget> _libraryConstants = {};
-
- final Set<ConstantEvaluationTarget> _constants = {};
-
- final String Function(FileState file) getFileContent;
-
- LibraryAnalyzer(
- this._analysisOptions,
- this._declaredVariables,
- this._sourceFactory,
- this._isLibraryUri,
- this._context,
- this._elementFactory,
- this._inheritance,
- this._library,
- this.getFileContent,
- );
-
- TypeProviderImpl get _typeProvider => _libraryElement.typeProvider;
-
- TypeSystemImpl get _typeSystem => _libraryElement.typeSystem;
-
- /// Compute analysis results for all units of the library.
- Map<FileState, UnitAnalysisResult> analyze({
- required String? completionPath,
- required int? completionOffset,
- required OperationPerformanceImpl performance,
- }) {
- var forCompletion = completionPath != null;
- var units = <FileState, CompilationUnitImpl>{};
-
- // Parse all files.
- performance.run('parse', (performance) {
- final libraryKind = _library.kind.asLibrary;
- for (FileState file in libraryKind.file.libraryFiles) {
- if (completionPath == null || file.path == completionPath) {
- units[file] = _parse(
- file: file,
- performance: performance,
- );
- }
- }
- });
-
- // Resolve URIs in directives to corresponding sources.
- FeatureSet featureSet = units.values.first.featureSet;
-
- performance.run('resolveUriDirectives', (performance) {
- units.forEach((file, unit) {
- _validateFeatureSet(unit, featureSet);
- _resolveUriBasedDirectives(file, unit);
- });
- });
-
- performance.run('libraryElement', (performance) {
- _libraryElement = _elementFactory.libraryOfUri2(_library.uri);
- });
-
- performance.run('resolveDirectives', (performance) {
- _resolveDirectives(units, completionPath);
- });
-
- performance.run('resolveFiles', (performance) {
- units.forEach((file, unit) {
- _resolveFile(
- completionOffset: completionOffset,
- file: file,
- unit: unit,
- );
- });
- });
-
- if (!forCompletion) {
- performance.run('computeConstants', (performance) {
- units.values.forEach(_findConstants);
- _clearConstantEvaluationResults();
- _computeConstants();
- });
-
- _computeDiagnostics(performance: performance, units: units);
- }
-
- assert(units.values.every(LegacyTypeAsserter.assertLegacyTypes));
-
- // Return full results.
- Map<FileState, UnitAnalysisResult> results = {};
- units.forEach((file, unit) {
- List<AnalysisError> errors = _getErrorListener(file).errors;
- errors = _filterIgnoredErrors(file, errors);
- results[file] = UnitAnalysisResult(file, unit, errors);
- });
- return results;
- }
-
- /// Clear evaluation results for all constants before computing them again.
- /// The reason is described in https://github.com/dart-lang/sdk/issues/35940
- ///
- /// Otherwise, we reuse results, including errors are recorded only when
- /// we evaluate constants resynthesized from summaries.
- ///
- /// TODO(scheglov) Remove after https://github.com/dart-lang/sdk/issues/31925
- void _clearConstantEvaluationResults() {
- for (var constant in _libraryConstants) {
- if (constant is ConstFieldElementImpl && constant.isEnumConstant) {
- continue;
- }
- if (constant is ConstVariableElement) {
- constant.evaluationResult = null;
- }
- }
- }
-
- void _computeConstantErrors(
- ErrorReporter errorReporter, CompilationUnit unit) {
- ConstantVerifier constantVerifier =
- ConstantVerifier(errorReporter, _libraryElement, _declaredVariables);
- unit.accept(constantVerifier);
- }
-
- /// Compute [_constants] in all units.
- void _computeConstants() {
- computeConstants(
- _declaredVariables, _constants.toList(), _libraryElement.featureSet);
- }
-
- void _computeDiagnostics({
- required OperationPerformanceImpl performance,
- required Map<FileState, CompilationUnit> units,
- }) {
- performance.run('computeVerifyErrors', (performance) {
- units.forEach((file, unit) {
- _computeVerifyErrors(file, unit);
- });
- });
-
- if (_analysisOptions.hint) {
- performance.run('computeHints', (performance) {
- units.forEach((file, unit) {
- {
- var visitor = GatherUsedLocalElementsVisitor(_libraryElement);
- unit.accept(visitor);
- _usedLocalElementsList.add(visitor.usedElements);
- }
- {
- var visitor = GatherUsedImportedElementsVisitor(_libraryElement);
- unit.accept(visitor);
- _usedImportedElementsList.add(visitor.usedElements);
- }
- });
- units.forEach((file, unit) {
- _computeHints(file, unit);
- });
- });
- }
-
- final libraryKind = _library.kind.asLibrary;
- final libraryFiles = libraryKind.file.libraryFiles.toList();
-
- if (_analysisOptions.lint) {
- performance.run('computeLints', (performance) {
- var allUnits = libraryFiles.map((file) {
- var content = getFileContent(file);
- return LinterContextUnit(content, units[file]!);
- }).toList();
- for (int i = 0; i < allUnits.length; i++) {
- _computeLints(libraryFiles[i], allUnits[i], allUnits);
- }
- });
- }
-
- // This must happen after all other diagnostics have been computed but
- // before the list of diagnostics has been filtered.
- for (var file in libraryFiles) {
- IgnoreValidator(
- _getErrorReporter(file),
- _getErrorListener(file).errors,
- _fileToIgnoreInfo[file]!,
- _fileToLineInfo[file]!,
- _analysisOptions.unignorableNames,
- ).reportErrors();
- }
- }
-
- void _computeHints(FileState file, CompilationUnit unit) {
- AnalysisErrorListener errorListener = _getErrorListener(file);
- ErrorReporter errorReporter = _getErrorReporter(file);
-
- if (!_libraryElement.isNonNullableByDefault) {
- unit.accept(
- LegacyDeadCodeVerifier(
- errorReporter,
- typeSystem: _typeSystem,
- ),
- );
- }
-
- unit.accept(DeadCodeVerifier(errorReporter));
-
- var content = getFileContent(file);
- UnicodeTextVerifier(errorReporter).verify(unit, content);
-
- unit.accept(
- BestPracticesVerifier(
- errorReporter,
- _typeProvider,
- _libraryElement,
- unit,
- content,
- declaredVariables: _declaredVariables,
- typeSystem: _typeSystem,
- inheritanceManager: _inheritance,
- analysisOptions: _context.analysisOptions,
- workspacePackage: _library.workspacePackage,
- ),
- );
-
- unit.accept(OverrideVerifier(
- _inheritance,
- _libraryElement,
- errorReporter,
- ));
-
- TodoFinder(errorReporter).findIn(unit);
-
- // Verify imports.
- {
- ImportsVerifier verifier = ImportsVerifier();
- verifier.addImports(unit);
- _usedImportedElementsList.forEach(verifier.removeUsedElements);
- verifier.generateDuplicateImportHints(errorReporter);
- verifier.generateDuplicateShownHiddenNameHints(errorReporter);
- verifier.generateUnusedImportHints(errorReporter);
- verifier.generateUnusedShownNameHints(errorReporter);
- }
-
- // Unused local elements.
- {
- UsedLocalElements usedElements =
- UsedLocalElements.merge(_usedLocalElementsList);
- UnusedLocalElementsVerifier visitor = UnusedLocalElementsVerifier(
- errorListener, usedElements, _inheritance, _libraryElement);
- unit.accept(visitor);
- }
-
- //
- // Find code that uses features from an SDK version that does not satisfy
- // the SDK constraints specified in analysis options.
- //
- var sdkVersionConstraint = _analysisOptions.sdkVersionConstraint;
- if (sdkVersionConstraint != null) {
- SdkConstraintVerifier verifier = SdkConstraintVerifier(
- errorReporter, _libraryElement, _typeProvider, sdkVersionConstraint);
- unit.accept(verifier);
- }
- }
-
- void _computeLints(FileState file, LinterContextUnit currentUnit,
- List<LinterContextUnit> allUnits) {
- var unit = currentUnit.unit;
-
- ErrorReporter errorReporter = _getErrorReporter(file);
-
- var nodeRegistry = NodeLintRegistry(_analysisOptions.enableTiming);
- final workspacePackage = _getPackage(currentUnit.unit);
- var context = LinterContextImpl(
- allUnits,
- currentUnit,
- _declaredVariables,
- _typeProvider,
- _typeSystem,
- _inheritance,
- _analysisOptions,
- workspacePackage);
- for (Linter linter in _analysisOptions.lintRules) {
- linter.reporter = errorReporter;
- linter.registerNodeProcessors(nodeRegistry, context);
- }
-
- // Run lints that handle specific node types.
- unit.accept(
- LinterVisitor(
- nodeRegistry,
- LinterExceptionHandler(
- propagateExceptions: _analysisOptions.propagateLinterExceptions,
- ).logException,
- ),
- );
- }
-
- void _computeVerifyErrors(FileState file, CompilationUnit unit) {
- ErrorReporter errorReporter = _getErrorReporter(file);
-
- if (!unit.featureSet.isEnabled(Feature.non_nullable)) {
- CodeChecker checker = CodeChecker(
- _typeProvider,
- _typeSystem,
- errorReporter,
- );
- checker.visitCompilationUnit(unit);
- }
-
- //
- // Validate the directives.
- //
- _validateUriBasedDirectives(file, unit);
-
- //
- // Use the ConstantVerifier to compute errors.
- //
- _computeConstantErrors(errorReporter, unit);
-
- //
- // Compute inheritance and override errors.
- //
- var inheritanceOverrideVerifier =
- InheritanceOverrideVerifier(_typeSystem, _inheritance, errorReporter);
- inheritanceOverrideVerifier.verifyUnit(unit);
-
- //
- // Use the ErrorVerifier to compute errors.
- //
- ErrorVerifier errorVerifier = ErrorVerifier(
- errorReporter, _libraryElement, _typeProvider, _inheritance);
- unit.accept(errorVerifier);
- }
-
- /// Return a subset of the given [errors] that are not marked as ignored in
- /// the [file].
- List<AnalysisError> _filterIgnoredErrors(
- FileState file, List<AnalysisError> errors) {
- if (errors.isEmpty) {
- return errors;
- }
-
- IgnoreInfo ignoreInfo = _fileToIgnoreInfo[file]!;
- if (!ignoreInfo.hasIgnores) {
- return errors;
- }
-
- LineInfo lineInfo = _fileToLineInfo[file]!;
-
- bool isIgnored(AnalysisError error) {
- int errorLine = lineInfo.getLocation(error.offset).lineNumber;
- return ignoreInfo.ignoredAt(error.errorCode, errorLine);
- }
-
- return errors.where((AnalysisError e) => !isIgnored(e)).toList();
- }
-
- /// Find constants to compute.
- void _findConstants(CompilationUnit unit) {
- ConstantFinder constantFinder = ConstantFinder();
- unit.accept(constantFinder);
- _libraryConstants.addAll(constantFinder.constantsToCompute);
- _constants.addAll(constantFinder.constantsToCompute);
-
- var dependenciesFinder = ConstantExpressionsDependenciesFinder();
- unit.accept(dependenciesFinder);
- _constants.addAll(dependenciesFinder.dependencies);
- }
-
- RecordingErrorListener _getErrorListener(FileState file) =>
- _errorListeners.putIfAbsent(file, () => RecordingErrorListener());
-
- ErrorReporter _getErrorReporter(FileState file) {
- return _errorReporters.putIfAbsent(file, () {
- RecordingErrorListener listener = _getErrorListener(file);
- return ErrorReporter(
- listener,
- file.source,
- isNonNullableByDefault: _libraryElement.isNonNullableByDefault,
- );
- });
- }
-
- WorkspacePackage? _getPackage(CompilationUnit unit) {
- final libraryPath = _library.source.fullName;
- final session = unit.declaredElement!.session;
- final workspace = session.analysisContext.contextRoot.workspace;
- return workspace.findPackageFor(libraryPath);
- }
-
- /// Return the name of the library that the given part is declared to be a
- /// part of, or `null` if the part does not contain a part-of directive.
- _NameOrSource? _getPartLibraryNameOrUri(Source partSource,
- CompilationUnit partUnit, List<Directive> directivesToResolve) {
- for (Directive directive in partUnit.directives) {
- if (directive is PartOfDirective) {
- directivesToResolve.add(directive);
- var libraryName = directive.libraryName;
- if (libraryName != null) {
- return _NameOrSource(libraryName.name, null);
- }
- var uri = directive.uri?.stringValue;
- if (uri != null) {
- var librarySource = _sourceFactory.resolveUri(partSource, uri);
- if (librarySource != null) {
- return _NameOrSource(null, librarySource);
- }
- }
- }
- }
- return null;
- }
-
- bool _isExistingSource(Source source) {
- final libraryKind = _library.kind.asLibrary;
- for (var file in libraryKind.file.directReferencedFiles) {
- if (file.uri == source.uri) {
- return file.exists;
- }
- }
- return false;
- }
-
- /// Return `true` if the given [source] is a library.
- bool _isLibrarySource(Source source) {
- return _isLibraryUri(source.uri);
- }
-
- /// Return a parsed unresolved [CompilationUnit].
- CompilationUnitImpl _parse({
- required FileState file,
- required OperationPerformanceImpl performance,
- }) {
- String content = getFileContent(file);
-
- performance.getDataInt('count').increment();
- performance.getDataInt('length').add(content.length);
-
- AnalysisErrorListener errorListener = _getErrorListener(file);
- var unit = file.parse2(errorListener, content);
-
- LineInfo lineInfo = unit.lineInfo;
- _fileToLineInfo[file] = lineInfo;
- _fileToIgnoreInfo[file] = IgnoreInfo.forDart(unit, content);
-
- return unit;
- }
-
- void _resolveDirectives(
- Map<FileState, CompilationUnitImpl> units,
- String? completionPath,
- ) {
- if (completionPath != null) {
- var completionUnit = units.values.first;
- var unitElement = _unitElementWithPath(completionPath);
- // TODO(scheglov) https://github.com/dart-lang/sdk/issues/44840
- if (unitElement == null) {
- String shortString(String s) {
- const maxLength = 1000;
- if (s.length > maxLength) {
- return s.substring(0, maxLength);
- }
- return s;
- }
-
- var libraryContent = '<unknown>';
- try {
- libraryContent = _library.getContent();
- libraryContent = shortString(libraryContent);
- } catch (_) {}
-
- var libraryUnitPaths =
- _libraryElement.units.map((e) => e.source.fullName).toList();
- throw '[completionPath: $completionPath]'
- '[library.path: ${_library.path}]'
- '[library.uri: ${_library.uri}]'
- '[libraryUnitPaths: $libraryUnitPaths]'
- '[libraryContent: $libraryContent]'
- '[unitStr: ${shortString('$completionUnit')}]';
- }
- completionUnit.element = unitElement;
- return;
- }
-
- final libraryKind = _library.kind.asLibrary;
-
- var definingCompilationUnit = units[_library]!;
- definingCompilationUnit.element = _libraryElement.definingCompilationUnit;
-
- bool matchNodeElement(Directive node, Element element) {
- return node.keyword.offset == element.nameOffset;
- }
-
- ErrorReporter libraryErrorReporter = _getErrorReporter(_library);
-
- LibraryIdentifier? libraryNameNode;
- var seenPartSources = <Source>{};
- var directivesToResolve = <DirectiveImpl>[];
- int partIndex = 0;
- for (Directive directive in definingCompilationUnit.directives) {
- if (directive is LibraryDirectiveImpl) {
- libraryNameNode = directive.name;
- directivesToResolve.add(directive);
- } else if (directive is ImportDirectiveImpl) {
- for (ImportElement importElement in _libraryElement.imports) {
- if (matchNodeElement(directive, importElement)) {
- directive.element = importElement;
- directive.prefix?.staticElement = importElement.prefix;
- var source = importElement.importedLibrary?.source;
- if (source != null && !_isLibrarySource(source)) {
- // It is safe to assume that `directive.uri.stringValue` is
- // non-`null`, because the only time it is `null` is if the URI
- // contains a string interpolation, in which case the import
- // would never have resolved in the first place.
- ErrorCode errorCode = CompileTimeErrorCode.IMPORT_OF_NON_LIBRARY;
- libraryErrorReporter.reportErrorForNode(
- errorCode, directive.uri, [directive.uri.stringValue!]);
- }
- }
- }
- } else if (directive is ExportDirectiveImpl) {
- for (ExportElement exportElement in _libraryElement.exports) {
- if (matchNodeElement(directive, exportElement)) {
- directive.element = exportElement;
- var source = exportElement.exportedLibrary?.source;
- if (source != null && !_isLibrarySource(source)) {
- // It is safe to assume that `directive.uri.stringValue` is
- // non-`null`, because the only time it is `null` is if the URI
- // contains a string interpolation, in which case the export
- // would never have resolved in the first place.
- libraryErrorReporter.reportErrorForNode(
- CompileTimeErrorCode.EXPORT_OF_NON_LIBRARY,
- directive.uri,
- [directive.uri.stringValue!]);
- }
- }
- }
- } else if (directive is PartDirectiveImpl) {
- StringLiteral partUri = directive.uri;
-
- FileState partFile = libraryKind.file.partedFiles[partIndex]!;
- var partUnit = units[partFile]!;
- CompilationUnitElement partElement = _libraryElement.parts[partIndex];
- partUnit.element = partElement;
- directive.element = partElement;
- partIndex++;
-
- var partSource = directive.uriSource;
- if (partSource == null) {
- continue;
- }
-
- //
- // Validate that the part source is unique in the library.
- //
- if (!seenPartSources.add(partSource)) {
- libraryErrorReporter.reportErrorForNode(
- CompileTimeErrorCode.DUPLICATE_PART, partUri, [partSource.uri]);
- }
-
- //
- // Validate that the part contains a part-of directive with the same
- // name or uri as the library.
- //
- if (_isExistingSource(partSource)) {
- var nameOrSource = _getPartLibraryNameOrUri(
- partSource, partUnit, directivesToResolve);
- if (nameOrSource == null) {
- libraryErrorReporter.reportErrorForNode(
- CompileTimeErrorCode.PART_OF_NON_PART,
- partUri,
- [partUri.toSource()]);
- } else {
- var name = nameOrSource.name;
- if (name != null) {
- if (libraryNameNode == null) {
- libraryErrorReporter.reportErrorForNode(
- CompileTimeErrorCode.PART_OF_UNNAMED_LIBRARY,
- partUri,
- [name]);
- } else if (libraryNameNode.name != name) {
- libraryErrorReporter.reportErrorForNode(
- CompileTimeErrorCode.PART_OF_DIFFERENT_LIBRARY,
- partUri,
- [libraryNameNode.name, name]);
- }
- } else {
- var source = nameOrSource.source!;
- if (source != _library.source) {
- libraryErrorReporter.reportErrorForNode(
- CompileTimeErrorCode.PART_OF_DIFFERENT_LIBRARY,
- partUri,
- [_library.uriStr, source.uri]);
- }
- }
- }
- }
- }
- }
-
- // TODO(brianwilkerson) Report the error
- // ResolverErrorCode.MISSING_LIBRARY_DIRECTIVE_WITH_PART
-
- //
- // Resolve the relevant directives to the library element.
- //
- for (var directive in directivesToResolve) {
- directive.element = _libraryElement;
- }
- }
-
- void _resolveFile({
- required int? completionOffset,
- required FileState file,
- required CompilationUnit unit,
- }) {
- Source source = file.source;
-
- RecordingErrorListener errorListener = _getErrorListener(file);
-
- var unitElement = unit.declaredElement as CompilationUnitElementImpl;
-
- unit.accept(
- ResolutionVisitor(
- unitElement: unitElement,
- errorListener: errorListener,
- featureSet: unit.featureSet,
- nameScope: _libraryElement.scope,
- elementWalker: ElementWalker.forCompilationUnit(unitElement),
- ),
- );
-
- unit.accept(ScopeResolverVisitor(
- _libraryElement, source, _typeProvider, errorListener,
- nameScope: _libraryElement.scope));
-
- // Nothing for RESOLVED_UNIT8?
- // Nothing for RESOLVED_UNIT9?
- // Nothing for RESOLVED_UNIT10?
-
- FlowAnalysisHelper flowAnalysisHelper =
- FlowAnalysisHelper(_typeSystem, false, unit.featureSet);
-
- var resolverVisitor = ResolverVisitor(
- _inheritance, _libraryElement, source, _typeProvider, errorListener,
- featureSet: unit.featureSet, flowAnalysisHelper: flowAnalysisHelper);
-
- var donePartialResolution = false;
- if (completionOffset != null) {
- var node = NodeLocator(completionOffset).searchWithin(unit);
- var nodeToResolve = node?.thisOrAncestorMatching((e) {
- return e.parent is ClassDeclaration ||
- e.parent is CompilationUnit ||
- e.parent is MixinDeclaration;
- });
- if (nodeToResolve != null) {
- var can = resolverVisitor.prepareForResolving(nodeToResolve);
- if (can) {
- nodeToResolve.accept(resolverVisitor);
- donePartialResolution = true;
- }
- }
- }
-
- if (!donePartialResolution) {
- unit.accept(resolverVisitor);
- }
- }
-
- /// Return the result of resolve the given [uriContent], reporting errors
- /// against the [uriLiteral].
- Source? _resolveUri(FileState file, bool isImport, StringLiteral uriLiteral,
- String? uriContent) {
- var code =
- UriBasedDirectiveImpl.validateUri(isImport, uriLiteral, uriContent);
- if (code == null) {
- return _sourceFactory.resolveUri(file.source, uriContent);
- } else if (code == UriValidationCode.URI_WITH_INTERPOLATION) {
- _getErrorReporter(file).reportErrorForNode(
- CompileTimeErrorCode.URI_WITH_INTERPOLATION, uriLiteral);
- return null;
- } else if (code == UriValidationCode.INVALID_URI) {
- // It is safe to assume [uriContent] is non-null because the only way for
- // it to be null is if the string literal contained an interpolation, and
- // in that case the validation code would have been
- // UriValidationCode.URI_WITH_INTERPOLATION.
- _getErrorReporter(file).reportErrorForNode(
- CompileTimeErrorCode.INVALID_URI, uriLiteral, [uriContent!]);
- return null;
- }
- return null;
- }
-
- void _resolveUriBasedDirectives(FileState file, CompilationUnit unit) {
- for (var directive in unit.directives) {
- if (directive is UriBasedDirectiveImpl) {
- StringLiteral uriLiteral = directive.uri;
- var uriContent = uriLiteral.stringValue?.trim();
- directive.uriContent = uriContent;
- var defaultSource = _resolveUri(
- file, directive is ImportDirective, uriLiteral, uriContent);
- directive.uriSource = defaultSource;
- }
- }
- }
-
- CompilationUnitElement? _unitElementWithPath(String path) {
- for (var unitElement in _libraryElement.units) {
- if (unitElement.source.fullName == path) {
- return unitElement;
- }
- }
- return null;
- }
-
- /// Validate that the feature set associated with the compilation [unit] is
- /// the same as the [expectedSet] of features supported by the library.
- void _validateFeatureSet(CompilationUnit unit, FeatureSet expectedSet) {
- FeatureSet actualSet = unit.featureSet;
- if (actualSet != expectedSet) {
- // TODO(brianwilkerson) Generate a diagnostic.
- }
- }
-
- /// Check the given [directive] to see if the referenced source exists and
- /// report an error if it does not.
- void _validateUriBasedDirective(
- FileState file, UriBasedDirectiveImpl directive) {
- var source = directive.uriSource;
- if (source != null) {
- if (_isExistingSource(source)) {
- return;
- }
- } else {
- // Don't report errors already reported by ParseDartTask.resolveDirective
- // TODO(scheglov) we don't use this task here
- if (directive.validate() != null) {
- return;
- }
- }
-
- var uriContent = directive.uriContent;
- if (uriContent != null && uriContent.startsWith('dart-ext:')) {
- _getErrorReporter(file).reportErrorForNode(
- CompileTimeErrorCode.USE_OF_NATIVE_EXTENSION,
- directive.uri,
- );
- return;
- }
-
- StringLiteral uriLiteral = directive.uri;
- CompileTimeErrorCode errorCode = CompileTimeErrorCode.URI_DOES_NOT_EXIST;
- if (isGeneratedSource(source)) {
- errorCode = CompileTimeErrorCode.URI_HAS_NOT_BEEN_GENERATED;
- }
- // It is safe to assume that `uriContent` is non-null because the only way
- // for it to be null is if the string literal contained an interpolation,
- // and in that case the call to `directive.validate()` above would have
- // returned a non-null validation code.
- _getErrorReporter(file)
- .reportErrorForNode(errorCode, uriLiteral, [uriContent!]);
- }
-
- /// Check each directive in the given [unit] to see if the referenced source
- /// exists and report an error if it does not.
- void _validateUriBasedDirectives(FileState file, CompilationUnit unit) {
- for (var directive in unit.directives) {
- if (directive is UriBasedDirectiveImpl) {
- _validateUriBasedDirective(file, directive);
- }
- }
- }
-}
-
-/// Analysis result for single file.
-class UnitAnalysisResult {
- final FileState file;
- final CompilationUnit unit;
- final List<AnalysisError> errors;
-
- UnitAnalysisResult(this.file, this.unit, this.errors);
-}
-
-/// Either the name or the source associated with a part-of directive.
-class _NameOrSource {
- final String? name;
- final Source? source;
-
- _NameOrSource(this.name, this.source);
-}
diff --git a/pkg/analyzer/lib/src/dart/micro/library_graph.dart b/pkg/analyzer/lib/src/dart/micro/library_graph.dart
deleted file mode 100644
index c182ed9..0000000
--- a/pkg/analyzer/lib/src/dart/micro/library_graph.dart
+++ /dev/null
@@ -1,1182 +0,0 @@
-// Copyright (c) 2020, 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:convert';
-import 'dart:typed_data';
-
-import 'package:_fe_analyzer_shared/src/scanner/token_impl.dart';
-import 'package:_fe_analyzer_shared/src/util/dependency_walker.dart' as graph
- show DependencyWalker, Node;
-import 'package:analyzer/dart/analysis/features.dart';
-import 'package:analyzer/dart/ast/ast.dart';
-import 'package:analyzer/dart/ast/token.dart';
-import 'package:analyzer/dart/element/element.dart';
-import 'package:analyzer/error/listener.dart';
-import 'package:analyzer/file_system/file_system.dart';
-import 'package:analyzer/src/dart/analysis/byte_store.dart';
-import 'package:analyzer/src/dart/analysis/experiments.dart';
-import 'package:analyzer/src/dart/analysis/feature_set_provider.dart';
-import 'package:analyzer/src/dart/analysis/unlinked_api_signature.dart';
-import 'package:analyzer/src/dart/analysis/unlinked_data.dart';
-import 'package:analyzer/src/dart/ast/ast.dart';
-import 'package:analyzer/src/dart/scanner/reader.dart';
-import 'package:analyzer/src/dart/scanner/scanner.dart';
-import 'package:analyzer/src/generated/parser.dart';
-import 'package:analyzer/src/generated/source.dart';
-import 'package:analyzer/src/generated/utilities_dart.dart';
-import 'package:analyzer/src/summary/api_signature.dart';
-import 'package:analyzer/src/summary2/data_reader.dart';
-import 'package:analyzer/src/summary2/data_writer.dart';
-import 'package:analyzer/src/summary2/informative_data.dart';
-import 'package:analyzer/src/util/file_paths.dart' as file_paths;
-import 'package:analyzer/src/util/performance/operation_performance.dart';
-import 'package:analyzer/src/workspace/workspace.dart';
-import 'package:collection/collection.dart';
-import 'package:convert/convert.dart';
-import 'package:meta/meta.dart';
-import 'package:pub_semver/pub_semver.dart';
-
-/// Ensure that the [FileState.libraryCycle] for the [file] and anything it
-/// depends on is computed.
-void computeLibraryCycle(Uint32List linkedSalt, FileState file) {
- var libraryWalker = _LibraryWalker(linkedSalt);
- libraryWalker.walk(libraryWalker.getNode(file));
-}
-
-class CiderUnlinkedUnit {
- /// Top-level declarations of the unit.
- final Set<String> topLevelDeclarations;
-
- /// Unlinked summary of the compilation unit.
- final UnlinkedUnit unit;
-
- CiderUnlinkedUnit({
- required this.topLevelDeclarations,
- required this.unit,
- });
-
- factory CiderUnlinkedUnit.fromBytes(Uint8List bytes) {
- return CiderUnlinkedUnit.read(
- SummaryDataReader(bytes),
- );
- }
-
- factory CiderUnlinkedUnit.read(SummaryDataReader reader) {
- return CiderUnlinkedUnit(
- topLevelDeclarations: reader.readStringUtf8Set(),
- unit: UnlinkedUnit.read(reader),
- );
- }
-
- Uint8List toBytes() {
- var byteSink = ByteSink();
- var sink = BufferedSink(byteSink);
- write(sink);
- return sink.flushAndTake();
- }
-
- void write(BufferedSink sink) {
- sink.writeStringUtf8Iterable(topLevelDeclarations);
- unit.write(sink);
- }
-}
-
-class FileState {
- final _FileStateUnlinked _unlinked;
-
- /// Files that reference this file.
- final List<FileState> referencingFiles = [];
-
- FileStateFiles? _files;
-
- LibraryCycle? _libraryCycle;
-
- FileState._(this._unlinked);
-
- Uint8List get apiSignature => unlinkedUnit.apiSignature;
-
- Uint8List get digest => _unlinked.digest;
-
- bool get exists => _unlinked.exists;
-
- /// Return `true` if the file does not have a `library` directive, and has a
- /// `part of` directive, so is probably a part.
- bool get isPart {
- if (unlinkedUnit.libraryDirective != null) {
- return false;
- }
- return unlinkedUnit.partOfNameDirective != null ||
- unlinkedUnit.partOfUriDirective != null;
- }
-
- /// Return the [LibraryCycle] this file belongs to, even if it consists of
- /// just this file. If the library cycle is not known yet, compute it.
- LibraryCycle get libraryCycle {
- if (_libraryCycle == null) {
- computeLibraryCycle(_fsState._linkedSalt, this);
- }
- return _libraryCycle!;
- }
-
- LineInfo get lineInfo => LineInfo(unlinkedUnit.lineStarts);
-
- FileState? get partOfLibrary => _unlinked.partOfLibrary;
-
- String get path => _location.path;
-
- /// The resolved signature of the file, that depends on the [libraryCycle]
- /// signature, and the content of the file.
- String get resolvedSignature {
- var signatureBuilder = ApiSignature();
- signatureBuilder.addString(path);
- signatureBuilder.addBytes(libraryCycle.signature);
-
- var content = getContent();
- signatureBuilder.addString(content);
-
- return signatureBuilder.toHex();
- }
-
- File get resource => _location.resource;
-
- Source get source => _location.source;
-
- String get unlinkedKey => _unlinked.unlinkedKey;
-
- UnlinkedUnit get unlinkedUnit => _unlinked.unlinked.unit;
-
- Uri get uri => _location.uri;
-
- /// Return the [uri] string.
- String get uriStr => uri.toString();
-
- WorkspacePackage? get workspacePackage => _location.workspacePackage;
-
- FileSystemState get _fsState => _location._fsState;
-
- _FileStateLocation get _location => _unlinked.location;
-
- /// Collect all files that are transitively referenced by this file via
- /// imports, exports, and parts.
- void collectAllReferencedFiles(Set<String> referencedFiles) {
- for (var file in files().directReferencedFiles) {
- if (referencedFiles.add(file.path)) {
- file.collectAllReferencedFiles(referencedFiles);
- }
- }
- }
-
- FileStateFiles files({
- OperationPerformanceImpl? performance,
- }) {
- return _files ??= FileStateFiles(
- owner: this,
- performance: performance ?? OperationPerformanceImpl('<root>'),
- );
- }
-
- /// Return the content of the file, the empty string if cannot be read.
- ///
- /// We read the file digest, end verify that it is the same as the digest
- /// that was recorded during the file creation. If it is not, then the file
- /// was changed, and we failed to call [FileSystemState.changeFile].
- String getContent() {
- var contentWithDigest = _location._getContent();
-
- var digest = contentWithDigest.digest;
- if (!const ListEquality<int>().equals(digest, _unlinked.digest)) {
- throw StateError('File was changed, but not invalidated: $path');
- }
-
- return contentWithDigest.content;
- }
-
- void internal_setLibraryCycle(LibraryCycle cycle, String signature) {
- _libraryCycle = cycle;
- }
-
- CompilationUnitImpl parse(
- AnalysisErrorListener errorListener, String content) {
- return _FileStateUnlinked.parse(errorListener, _location, content);
- }
-
- @override
- String toString() {
- return path;
- }
-}
-
-class FileStateFiles {
- final List<FileState> imported = [];
- final List<FileState> exported = [];
- final List<FileState> parted = [];
- final List<FileState> ofLibrary = [];
-
- FileStateFiles({
- required FileState owner,
- required OperationPerformanceImpl performance,
- }) {
- var unlinked = owner._unlinked;
- var location = unlinked.location;
- var unlinkedUnit = unlinked.unlinked.unit;
-
- // Build the graph.
- for (var directive in unlinkedUnit.imports) {
- var file = location._fileForRelativeUri(
- relativeUri: directive.uri,
- performance: performance,
- );
- if (file != null) {
- file.referencingFiles.add(owner);
- imported.add(file);
- }
- }
- for (var directive in unlinkedUnit.exports) {
- var file = location._fileForRelativeUri(
- relativeUri: directive.uri,
- performance: performance,
- );
- if (file != null) {
- exported.add(file);
- file.referencingFiles.add(owner);
- }
- }
- for (var uri in unlinkedUnit.parts) {
- var file = location._fileForRelativeUri(
- containingLibrary: owner,
- relativeUri: uri,
- performance: performance,
- );
- if (file != null) {
- parted.add(file);
- file.referencingFiles.add(owner);
- }
- }
-
- ofLibrary.add(owner);
- ofLibrary.addAll(parted);
- }
-
- /// Return all directly referenced files - imported, exported or parted.
- Set<FileState> get directReferencedFiles {
- return <FileState>{...imported, ...exported, ...parted};
- }
-
- /// Return all directly referenced libraries - imported or exported.
- Set<FileState> get directReferencedLibraries {
- return <FileState>{...imported, ...exported};
- }
-}
-
-class FileSystemState {
- final ResourceProvider _resourceProvider;
- final ByteStore _byteStore;
- final SourceFactory _sourceFactory;
- final Workspace _workspace;
- final Uint32List _linkedSalt;
-
- /// A function that returns the digest for a file as a String. The function
- /// returns a non null value, returns an empty string if file does
- /// not exist/has no contents.
- final String Function(String path) getFileDigest;
-
- final Map<String, FileState> _pathToFile = {};
- final Map<Uri, FileState> _uriToFile = {};
-
- final FeatureSetProvider featureSetProvider;
-
- /// A function that fetches the given list of files. This function can be used
- /// to batch file reads in systems where file fetches are expensive.
- final void Function(List<String> paths)? prefetchFiles;
-
- /// A function that returns true if the given file path is likely to be that
- /// of a file that is generated.
- final bool Function(String path)? isGenerated;
-
- final FileSystemStateTimers timers2 = FileSystemStateTimers();
-
- final FileSystemStateTestView testView = FileSystemStateTestView();
-
- FileSystemTestData? testData;
-
- FileSystemState(
- this._resourceProvider,
- this._byteStore,
- this._sourceFactory,
- this._workspace,
- this._linkedSalt,
- this.featureSetProvider,
- this.getFileDigest,
- this.prefetchFiles,
- this.isGenerated,
- );
-
- /// Update the state to reflect the fact that the file with the given [path]
- /// was changed. Specifically this means that we evict this file and every
- /// file that referenced it.
- void changeFile(String path, List<FileState> removedFiles) {
- var file = _pathToFile.remove(path);
- if (file == null) {
- return;
- }
-
- removedFiles.add(file);
- _uriToFile.remove(file.uri);
-
- // The removed file does not reference other file anymore.
- for (var referencedFile in file.files().directReferencedFiles) {
- referencedFile.referencingFiles.remove(file);
- }
-
- // Recursively remove files that reference the removed file.
- for (var reference in file.referencingFiles.toList()) {
- changeFile(reference.path, removedFiles);
- }
- }
-
- FeatureSet contextFeatureSet(
- String path,
- Uri uri,
- WorkspacePackage? workspacePackage,
- ) {
- var workspacePackageExperiments = workspacePackage?.enabledExperiments;
- if (workspacePackageExperiments != null) {
- return featureSetProvider.featureSetForExperiments(
- workspacePackageExperiments,
- );
- }
-
- return featureSetProvider.getFeatureSet(path, uri);
- }
-
- Version contextLanguageVersion(
- String path,
- Uri uri,
- WorkspacePackage? workspacePackage,
- ) {
- var workspaceLanguageVersion = workspacePackage?.languageVersion;
- if (workspaceLanguageVersion != null) {
- return workspaceLanguageVersion;
- }
-
- return featureSetProvider.getLanguageVersion(path, uri);
- }
-
- /// Notifies this object that it is about to be discarded.
- ///
- /// Returns the keys of the artifacts that are no longer used.
- Set<String> dispose() {
- final result = <String>{};
- for (final file in _pathToFile.values) {
- result.add(file._unlinked.unlinkedKey);
- }
- _pathToFile.clear();
- _uriToFile.clear();
- return result;
- }
-
- @visibleForTesting
- FileState? getExistingFileForResource(File file) {
- return _pathToFile[file.path];
- }
-
- FileState getFileForPath({
- required String path,
- required OperationPerformanceImpl performance,
- }) {
- var file = _pathToFile[path];
- if (file != null) {
- return file;
- }
-
- var uri = _sourceFactory.pathToUri(path);
- if (uri == null) {
- throw StateError('Unable to convert path to URI: $path');
- }
-
- var source = _sourceFactory.forUri2(uri);
- if (source == null) {
- throw StateError('Unable to resolve URI: $uri, path: $path');
- }
-
- return _newFile(
- source: source,
- performance: performance,
- );
- }
-
- FileState? getFileForUri({
- FileState? containingLibrary,
- required Uri uri,
- required OperationPerformanceImpl performance,
- }) {
- var file = _uriToFile[uri];
- if (file != null) {
- return file;
- }
-
- var source = _sourceFactory.forUri2(uri);
- if (source == null) {
- return null;
- }
-
- return _newFile(
- source: source,
- performance: performance,
- );
- }
-
- /// Returns a list of files whose contents contains the given string.
- /// Generated files are not included in the search.
- List<String> getFilesContaining(String value) {
- var result = <String>[];
- _pathToFile.forEach((path, file) {
- var genFile = isGenerated == null ? false : isGenerated!(path);
- if (!genFile && file.getContent().contains(value)) {
- result.add(path);
- }
- });
- return result;
- }
-
- /// Return files that have a top-level declaration with the [name].
- List<FileState> getFilesWithTopLevelDeclarations(String name) {
- var result = <FileState>[];
- for (var file in _pathToFile.values) {
- if (file._unlinked.unlinked.topLevelDeclarations.contains(name)) {
- result.add(file);
- }
- }
- return result;
- }
-
- String? getPathForUri(Uri uri) {
- return _sourceFactory.forUri2(uri)?.fullName;
- }
-
- /// Computes the set of [FileState]'s used/not used to analyze the given
- /// [files]. Removes the [FileState]'s of the files not used for analysis from
- /// the cache. Returns the set of unused [FileState]'s.
- List<FileState> removeUnusedFiles(List<String> files) {
- var allReferenced = <String>{};
- for (var path in files) {
- allReferenced.add(path);
- _pathToFile[path]?.collectAllReferencedFiles(allReferenced);
- }
-
- var unusedPaths = _pathToFile.keys.toSet();
- unusedPaths.removeAll(allReferenced);
-
- var removedFiles = <FileState>[];
- for (var path in unusedPaths) {
- var file = _pathToFile.remove(path)!;
- _uriToFile.remove(file.uri);
- removedFiles.add(file);
- }
-
- return removedFiles;
- }
-
- FileState _newFile({
- required Source source,
- required OperationPerformanceImpl performance,
- }) {
- var path = source.fullName;
- var uri = source.uri;
-
- var workspacePackage = _workspace.findPackageFor(path);
- var featureSet = contextFeatureSet(path, uri, workspacePackage);
- var packageLanguageVersion =
- contextLanguageVersion(path, uri, workspacePackage);
-
- var location = _FileStateLocation._(this, path, uri, source,
- workspacePackage, featureSet, packageLanguageVersion);
- var file = FileState._(
- _FileStateUnlinked(
- location: location,
- partOfLibrary: null,
- performance: performance,
- ),
- );
- _pathToFile[path] = file;
- _uriToFile[uri] = file;
-
- // Recurse with recording performance.
- file.files(performance: performance);
-
- return file;
- }
-}
-
-class FileSystemStateTestView {
- final List<String> partsDiscoveredLibraries = [];
-}
-
-class FileSystemStateTimer {
- final Stopwatch timer = Stopwatch();
-
- T run<T>(T Function() f) {
- timer.start();
- try {
- return f();
- } finally {
- timer.stop();
- }
- }
-
- Future<T> runAsync<T>(T Function() f) async {
- timer.start();
- try {
- return f();
- } finally {
- timer.stop();
- }
- }
-}
-
-class FileSystemStateTimers {
- final FileSystemStateTimer digest = FileSystemStateTimer();
- final FileSystemStateTimer read = FileSystemStateTimer();
- final FileSystemStateTimer parse = FileSystemStateTimer();
- final FileSystemStateTimer unlinked = FileSystemStateTimer();
- final FileSystemStateTimer prefetch = FileSystemStateTimer();
-
- void reset() {
- digest.timer.reset();
- read.timer.reset();
- parse.timer.reset();
- unlinked.timer.reset();
- prefetch.timer.reset();
- }
-}
-
-class FileSystemTestData {
- final Map<File, FileTestData> files = {};
-
- FileTestData forFile(File file) {
- return files[file] ??= FileTestData._(file);
- }
-}
-
-class FileTestData {
- final File file;
-
- /// We add the key every time we get unlinked data from the byte store.
- final List<String> unlinkedKeyGet = [];
-
- /// We add the key every time we put unlinked data into the byte store.
- final List<String> unlinkedKeyPut = [];
-
- FileTestData._(this.file);
-}
-
-/// Information about libraries that reference each other, so form a cycle.
-class LibraryCycle {
- /// The libraries that belong to this cycle.
- final List<FileState> libraries = [];
-
- /// The library cycles that this cycle references directly.
- final Set<LibraryCycle> directDependencies = <LibraryCycle>{};
-
- /// The transitive signature of this cycle.
- ///
- /// It is based on the API signatures of all files of the [libraries], and
- /// the signatures of the cycles that the [libraries] reference
- /// directly. So, indirectly it is based on the transitive closure of all
- /// files that [libraries] reference (but we don't compute these files).
- late Uint8List signature;
-
- /// The hash of all the paths of the files in this cycle.
- late String cyclePathsHash;
-
- /// The key of the resolution cache entry.
- /// It is `null` if we failed to load libraries of the cycle.
- String? resolutionKey;
-
- LibraryCycle();
-
- String get signatureStr {
- return hex.encode(signature);
- }
-
- @override
- String toString() {
- return '[${libraries.join(', ')}]';
- }
-}
-
-class _ContentWithDigest {
- final String content;
- final Uint8List digest;
-
- _ContentWithDigest({
- required this.content,
- required this.digest,
- });
-}
-
-class _FileStateLocation {
- final FileSystemState _fsState;
-
- /// The path of the file.
- final String path;
-
- /// The URI of the file.
- final Uri uri;
-
- /// The [Source] of the file with the [uri].
- final Source source;
-
- /// The [WorkspacePackage] that contains this file.
- ///
- /// It might be `null` if the file is outside of the workspace.
- final WorkspacePackage? workspacePackage;
-
- /// The [FeatureSet] for all files in the analysis context.
- ///
- /// Usually it is the feature set of the latest language version, plus
- /// possibly additional enabled experiments (from the analysis options file,
- /// or from SDK allowed experiments).
- ///
- /// This feature set is then restricted, with the [_packageLanguageVersion],
- /// or with a `@dart` language override token in the file header.
- final FeatureSet _contextFeatureSet;
-
- /// The language version for the package that contains this file.
- final Version _packageLanguageVersion;
-
- _FileStateLocation._(
- this._fsState,
- this.path,
- this.uri,
- this.source,
- this.workspacePackage,
- this._contextFeatureSet,
- this._packageLanguageVersion,
- );
-
- File get resource {
- return _fsState._resourceProvider.getFile(path);
- }
-
- Uri? resolveRelativeUriStr(String relativeUriStr) {
- if (relativeUriStr.isEmpty) {
- return null;
- }
-
- Uri relativeUri;
- try {
- relativeUri = Uri.parse(relativeUriStr);
- } on FormatException {
- return null;
- }
-
- return resolveRelativeUri(uri, relativeUri);
- }
-
- FileState? _fileForRelativeUri({
- FileState? containingLibrary,
- required String relativeUri,
- required OperationPerformanceImpl performance,
- }) {
- var absoluteUri = resolveRelativeUriStr(relativeUri);
- if (absoluteUri == null) {
- return null;
- }
-
- return _fsState.getFileForUri(
- containingLibrary: containingLibrary,
- uri: absoluteUri,
- performance: performance,
- );
- }
-
- /// This file has a `part of some.library;` directive. Because it does not
- /// specify the URI of the library, we don't know the library for sure.
- /// But usually the library is one of the sibling files.
- FileState? _findPartOfNameLibrary({
- required OperationPerformanceImpl performance,
- }) {
- var resourceProvider = _fsState._resourceProvider;
- var pathContext = resourceProvider.pathContext;
-
- var siblings = <Resource>[];
- try {
- siblings = resource.parent.getChildren();
- } catch (_) {}
-
- for (var sibling in siblings) {
- if (file_paths.isDart(pathContext, sibling.path)) {
- var siblingState = _fsState.getFileForPath(
- path: sibling.path,
- performance: performance,
- );
- if (siblingState.files().parted.any((part) => part.path == path)) {
- return siblingState;
- }
- }
- }
- return null;
- }
-
- _ContentWithDigest _getContent() {
- String content;
- try {
- content = resource.readAsStringSync();
- } catch (_) {
- content = '';
- }
-
- var digestStr = _fsState.getFileDigest(path);
- var digest = utf8.encode(digestStr) as Uint8List;
-
- return _ContentWithDigest(content: content, digest: digest);
- }
-}
-
-class _FileStateUnlinked {
- final _FileStateLocation location;
- FileState? _partOfLibrary;
-
- final Uint8List digest;
- final bool exists;
- final CiderUnlinkedUnit unlinked;
-
- /// Key of the cache entry with unlinked data.
- final String unlinkedKey;
-
- factory _FileStateUnlinked({
- required _FileStateLocation location,
- required FileState? partOfLibrary,
- required OperationPerformanceImpl performance,
- }) {
- final testData = location._fsState.testData?.forFile(location.resource);
-
- CiderUnlinkedUnit unlinked;
-
- var digest = performance.run('digest', (performance) {
- performance.getDataInt('count').increment();
- var digestStr = location._fsState.getFileDigest(location.path);
- return utf8.encode(digestStr) as Uint8List;
- });
-
- var exists = digest.isNotEmpty;
-
- final unlinkedKey = '${hex.encode(digest)}.unlinked';
- var isUnlinkedFromCache = true;
-
- // Prepare bytes of the unlinked bundle - existing or new.
- // TODO(migration): should not be nullable
- Uint8List? unlinkedBytes;
- {
- unlinkedBytes = location._fsState._byteStore.get(unlinkedKey);
-
- if (unlinkedBytes == null || unlinkedBytes.isEmpty) {
- isUnlinkedFromCache = false;
-
- var contentWithDigest = performance.run('content', (_) {
- return location._getContent();
- });
- digest = contentWithDigest.digest;
- var content = contentWithDigest.content;
-
- var unit = performance.run('parse', (performance) {
- performance.getDataInt('count').increment();
- performance.getDataInt('length').add(content.length);
- return parse(AnalysisErrorListener.NULL_LISTENER, location, content);
- });
-
- performance.run('unlinked', (performance) {
- var unlinkedUnit = serializeAstCiderUnlinked(unit);
- unlinkedBytes = unlinkedUnit.toBytes();
- performance.getDataInt('length').add(unlinkedBytes!.length);
- unlinkedBytes =
- location._fsState._byteStore.putGet(unlinkedKey, unlinkedBytes!);
- testData?.unlinkedKeyPut.add(unlinkedKey);
- });
-
- unlinked = CiderUnlinkedUnit.fromBytes(unlinkedBytes!);
- } else {
- testData?.unlinkedKeyGet.add(unlinkedKey);
- }
- }
-
- // Read the unlinked bundle.
- unlinked = CiderUnlinkedUnit.fromBytes(unlinkedBytes!);
-
- var result = _FileStateUnlinked._(
- location: location,
- partOfLibrary: partOfLibrary,
- digest: digest,
- exists: exists,
- unlinked: unlinked,
- unlinkedKey: unlinkedKey,
- );
- if (isUnlinkedFromCache) {
- performance.run('prefetch', (_) {
- result._prefetchDirectReferences();
- });
- }
- return result;
- }
-
- _FileStateUnlinked._({
- required this.location,
- required FileState? partOfLibrary,
- required this.digest,
- required this.exists,
- required this.unlinked,
- required this.unlinkedKey,
- }) : _partOfLibrary = partOfLibrary;
-
- FileState? get partOfLibrary {
- var partOfLibrary = _partOfLibrary;
- if (partOfLibrary != null) {
- return partOfLibrary;
- }
-
- var performance = OperationPerformanceImpl('<root>');
-
- var libraryName = unlinked.unit.partOfNameDirective?.name;
- if (libraryName != null) {
- location._fsState.testView.partsDiscoveredLibraries.add(location.path);
- return _partOfLibrary = location._findPartOfNameLibrary(
- performance: performance,
- );
- }
-
- var libraryUri = unlinked.unit.partOfUriDirective?.uri;
- if (libraryUri != null) {
- location._fsState.testView.partsDiscoveredLibraries.add(location.path);
- return _partOfLibrary = location._fileForRelativeUri(
- relativeUri: libraryUri,
- performance: performance,
- );
- }
-
- return null;
- }
-
- void _prefetchDirectReferences() {
- var prefetchFiles = location._fsState.prefetchFiles;
- if (prefetchFiles == null) {
- return;
- }
-
- var paths = <String>{};
-
- void addRelativeUri(String relativeUri) {
- var absoluteUri = location.resolveRelativeUriStr(relativeUri);
- if (absoluteUri != null) {
- var path = location._fsState.getPathForUri(absoluteUri);
- if (path != null) {
- paths.add(path);
- }
- }
- }
-
- var unlinkedUnit = unlinked.unit;
- for (var directive in unlinkedUnit.imports) {
- addRelativeUri(directive.uri);
- }
- for (var directive in unlinkedUnit.exports) {
- addRelativeUri(directive.uri);
- }
- for (var uri in unlinkedUnit.parts) {
- addRelativeUri(uri);
- }
-
- prefetchFiles(paths.toList());
- }
-
- static CompilationUnitImpl parse(AnalysisErrorListener errorListener,
- _FileStateLocation location, String content) {
- CharSequenceReader reader = CharSequenceReader(content);
- Scanner scanner = Scanner(location.source, reader, errorListener)
- ..configureFeatures(
- featureSetForOverriding: location._contextFeatureSet,
- featureSet: location._contextFeatureSet.restrictToVersion(
- location._packageLanguageVersion,
- ),
- );
- Token token = scanner.tokenize(reportScannerErrors: false);
- LineInfo lineInfo = LineInfo(scanner.lineStarts);
-
- // Pass the feature set from the scanner to the parser
- // because the scanner may have detected a language version comment
- // and downgraded the feature set it holds.
- Parser parser = Parser(
- location.source,
- errorListener,
- featureSet: scanner.featureSet,
- lineInfo: lineInfo,
- );
- parser.enableOptionalNewAndConst = true;
- var unit = parser.parseCompilationUnit(token);
-
- // StringToken uses a static instance of StringCanonicalizer, so we need
- // to clear it explicitly once we are done using it for this file.
- StringTokenImpl.canonicalizer.clear();
-
- // TODO(scheglov) Use actual versions.
- unit.languageVersion = LibraryLanguageVersion(
- package: ExperimentStatus.currentVersion,
- override: null,
- );
-
- return unit;
- }
-
- static CiderUnlinkedUnit serializeAstCiderUnlinked(CompilationUnit unit) {
- UnlinkedLibraryDirective? libraryDirective;
- UnlinkedLibraryAugmentationDirective? libraryAugmentationDirective;
- UnlinkedPartOfNameDirective? partOfNameDirective;
- UnlinkedPartOfUriDirective? partOfUriDirective;
- var augmentations = <UnlinkedImportAugmentationDirective>[];
- var exports = <UnlinkedNamespaceDirective>[];
- var imports = <UnlinkedNamespaceDirective>[];
- var parts = <String>[];
- var hasDartCoreImport = false;
- for (var directive in unit.directives) {
- if (directive is ExportDirective) {
- var builder = _serializeNamespaceDirective(directive);
- exports.add(builder);
- } else if (directive is ImportDirectiveImpl) {
- if (directive.augmentKeyword != null) {
- augmentations.add(
- UnlinkedImportAugmentationDirective(
- uri: directive.uri.stringValue ?? '',
- ),
- );
- } else {
- var builder = _serializeNamespaceDirective(directive);
- imports.add(builder);
- if (builder.uri == 'dart:core') {
- hasDartCoreImport = true;
- }
- }
- } else if (directive is LibraryAugmentationDirective) {
- final uri = directive.uri;
- final uriStr = uri.stringValue;
- if (uriStr != null) {
- libraryAugmentationDirective = UnlinkedLibraryAugmentationDirective(
- uri: uriStr,
- uriRange: UnlinkedSourceRange(
- offset: uri.offset,
- length: uri.length,
- ),
- );
- }
- } else if (directive is LibraryDirective) {
- libraryDirective = UnlinkedLibraryDirective(
- name: directive.name.components.map((e) => e.name).join('.'),
- );
- } else if (directive is PartDirective) {
- var uriStr = directive.uri.stringValue;
- parts.add(uriStr ?? '');
- } else if (directive is PartOfDirective) {
- final libraryName = directive.libraryName;
- final uri = directive.uri;
- if (libraryName != null) {
- partOfNameDirective = UnlinkedPartOfNameDirective(
- name: libraryName.name,
- nameRange: UnlinkedSourceRange(
- offset: libraryName.offset,
- length: libraryName.length,
- ),
- );
- } else if (uri != null) {
- final uriStr = uri.stringValue;
- if (uriStr != null) {
- partOfUriDirective = UnlinkedPartOfUriDirective(
- uri: uriStr,
- uriRange: UnlinkedSourceRange(
- offset: uri.offset,
- length: uri.length,
- ),
- );
- }
- }
- }
- }
- if (!hasDartCoreImport) {
- imports.add(
- UnlinkedNamespaceDirective(
- configurations: [],
- isSyntheticDartCoreImport: true,
- uri: 'dart:core',
- ),
- );
- }
-
- var topLevelDeclarations = <String>{};
- for (var declaration in unit.declarations) {
- if (declaration is ClassDeclaration) {
- topLevelDeclarations.add(declaration.name.name);
- } else if (declaration is EnumDeclaration) {
- topLevelDeclarations.add(declaration.name.name);
- } else if (declaration is ExtensionDeclaration) {
- var name = declaration.name;
- if (name != null) {
- topLevelDeclarations.add(name.name);
- }
- } else if (declaration is FunctionDeclaration) {
- topLevelDeclarations.add(declaration.name.name);
- } else if (declaration is MixinDeclaration) {
- topLevelDeclarations.add(declaration.name.name);
- } else if (declaration is TopLevelVariableDeclaration) {
- for (var variable in declaration.variables.variables) {
- topLevelDeclarations.add(variable.name.name);
- }
- }
- }
-
- var unlinkedUnit = UnlinkedUnit(
- apiSignature: computeUnlinkedApiSignature(unit),
- augmentations: augmentations,
- exports: exports,
- imports: imports,
- informativeBytes: writeUnitInformative(unit),
- libraryAugmentationDirective: libraryAugmentationDirective,
- libraryDirective: libraryDirective,
- lineStarts: Uint32List.fromList(unit.lineInfo.lineStarts),
- macroClasses: [],
- parts: parts,
- partOfNameDirective: partOfNameDirective,
- partOfUriDirective: partOfUriDirective,
- topLevelDeclarations: topLevelDeclarations,
- );
-
- return CiderUnlinkedUnit(
- unit: unlinkedUnit,
- topLevelDeclarations: topLevelDeclarations,
- );
- }
-
- static UnlinkedNamespaceDirective _serializeNamespaceDirective(
- NamespaceDirective directive,
- ) {
- return UnlinkedNamespaceDirective(
- configurations: directive.configurations.map((configuration) {
- var name = configuration.name.components.join('.');
- var value = configuration.value?.stringValue ?? '';
- return UnlinkedNamespaceDirectiveConfiguration(
- name: name,
- value: value,
- uri: configuration.uri.stringValue ?? '',
- );
- }).toList(),
- uri: directive.uri.stringValue ?? '',
- );
- }
-}
-
-/// Node in [_LibraryWalker].
-class _LibraryNode extends graph.Node<_LibraryNode> {
- final _LibraryWalker walker;
- final FileState file;
-
- _LibraryNode(this.walker, this.file);
-
- @override
- bool get isEvaluated => file._libraryCycle != null;
-
- @override
- List<_LibraryNode> computeDependencies() {
- return file.files().directReferencedLibraries.map(walker.getNode).toList();
- }
-}
-
-/// Helper that organizes dependencies of a library into topologically
-/// sorted [LibraryCycle]s.
-class _LibraryWalker extends graph.DependencyWalker<_LibraryNode> {
- final Uint32List _linkedSalt;
- final Map<FileState, _LibraryNode> nodesOfFiles = {};
-
- _LibraryWalker(this._linkedSalt);
-
- @override
- void evaluate(_LibraryNode v) {
- evaluateScc([v]);
- }
-
- @override
- void evaluateScc(List<_LibraryNode> scc) {
- var cycle = LibraryCycle();
-
- var signature = ApiSignature();
- signature.addUint32List(_linkedSalt);
-
- // Sort libraries to produce stable signatures.
- scc.sort((first, second) {
- var firstPath = first.file.path;
- var secondPath = second.file.path;
- return firstPath.compareTo(secondPath);
- });
-
- // Append direct referenced cycles.
- for (var node in scc) {
- var file = node.file;
- _appendDirectlyReferenced(cycle, signature, file.files().imported);
- _appendDirectlyReferenced(cycle, signature, file.files().exported);
- }
-
- // Fill the cycle with libraries.
- for (var node in scc) {
- cycle.libraries.add(node.file);
-
- signature.addString(node.file.uriStr);
-
- signature.addInt(node.file.files().ofLibrary.length);
- for (var file in node.file.files().ofLibrary) {
- signature.addBool(file.exists);
- signature.addBytes(file.apiSignature);
- }
- }
-
- // Compute the general library cycle signature.
- cycle.signature = signature.toByteList();
-
- // Compute the cycle file paths signature.
- var filePathsSignature = ApiSignature();
- for (var node in scc) {
- filePathsSignature.addString(node.file.path);
- }
- cycle.cyclePathsHash = filePathsSignature.toHex();
-
- // Compute library specific signatures.
- for (var node in scc) {
- var librarySignatureBuilder = ApiSignature()
- ..addString(node.file.uriStr)
- ..addBytes(cycle.signature);
- var librarySignature = librarySignatureBuilder.toHex();
-
- node.file.internal_setLibraryCycle(
- cycle,
- librarySignature,
- );
- }
- }
-
- _LibraryNode getNode(FileState file) {
- return nodesOfFiles.putIfAbsent(file, () => _LibraryNode(this, file));
- }
-
- void _appendDirectlyReferenced(
- LibraryCycle cycle,
- ApiSignature signature,
- List<FileState> directlyReferenced,
- ) {
- signature.addInt(directlyReferenced.length);
- for (var referencedLibrary in directlyReferenced) {
- var referencedCycle = referencedLibrary._libraryCycle;
- // We get null when the library is a part of the cycle being build.
- if (referencedCycle == null) continue;
-
- if (cycle.directDependencies.add(referencedCycle)) {
- signature.addBytes(referencedCycle.signature);
- }
- }
- }
-}
diff --git a/pkg/analyzer/lib/src/dart/micro/resolve_file.dart b/pkg/analyzer/lib/src/dart/micro/resolve_file.dart
index 8283d1d..ab7d15f 100644
--- a/pkg/analyzer/lib/src/dart/micro/resolve_file.dart
+++ b/pkg/analyzer/lib/src/dart/micro/resolve_file.dart
@@ -873,7 +873,10 @@
class FileResolverTestData {
final fileSystem = FileSystemTestData();
- final libraryContext = LibraryContextTestData();
+
+ late final libraryContext = LibraryContextTestData(
+ fileSystemTestData: fileSystem,
+ );
/// The paths of libraries which were resolved.
///
diff --git a/pkg/analyzer/test/src/dart/analysis/analyzer_state_printer.dart b/pkg/analyzer/test/src/dart/analysis/analyzer_state_printer.dart
index 9755612..1a318c2 100644
--- a/pkg/analyzer/test/src/dart/analysis/analyzer_state_printer.dart
+++ b/pkg/analyzer/test/src/dart/analysis/analyzer_state_printer.dart
@@ -17,6 +17,7 @@
final FileStateIdProvider fileStateIdProvider;
final KeyShorter keyShorter;
final LibraryContext libraryContext;
+ final bool omitSdkFiles;
final ResourceProvider resourceProvider;
final StringSink sink;
@@ -27,6 +28,7 @@
required this.fileStateIdProvider,
required this.keyShorter,
required this.libraryContext,
+ required this.omitSdkFiles,
required this.resourceProvider,
required this.sink,
});
@@ -138,8 +140,13 @@
}
void _writeFiles(FileSystemTestData testData) {
- final fileMap = testData.files;
- final fileDataList = fileMap.values.toList();
+ final fileDataList = <FileTestData>[];
+ for (final fileData in testData.files.values) {
+ if (omitSdkFiles && fileData.uri.isScheme('dart')) {
+ continue;
+ }
+ fileDataList.add(fileData);
+ }
fileDataList.sortBy((fileData) => fileData.file.path);
// Ask ID for every file in the sorted order, so that IDs are nice.
@@ -181,10 +188,19 @@
void _writeLibraryContext(LibraryContextTestData testData) {
_writelnWithIndent('libraryCycles');
_withIndent(() {
- final entries = testData.libraryCycles.entries
- .mapKey((key) => key.map(_posixPath).join(' '))
- .toList();
- entries.sortBy((e) => e.key);
+ final cyclesToPrint = <_LibraryCycleToPrint>[];
+ for (final entry in testData.libraryCycles.entries) {
+ if (omitSdkFiles && entry.key.any((e) => e.uri.isScheme('dart'))) {
+ continue;
+ }
+ cyclesToPrint.add(
+ _LibraryCycleToPrint(
+ entry.key.map((e) => _posixPath(e.file)).join(' '),
+ entry.value,
+ ),
+ );
+ }
+ cyclesToPrint.sortBy((e) => e.pathListStr);
final loadedBundlesMap = Map.fromEntries(
libraryContext.loadedBundles.map((cycle) {
@@ -196,10 +212,10 @@
}),
);
- for (final entry in entries) {
- _writelnWithIndent(entry.key);
+ for (final cycleToPrint in cyclesToPrint) {
+ _writelnWithIndent(cycleToPrint.pathListStr);
_withIndent(() {
- final current = loadedBundlesMap[entry.key];
+ final current = loadedBundlesMap[cycleToPrint.pathListStr];
if (current != null) {
_writelnWithIndent('current');
_withIndent(() {
@@ -213,8 +229,9 @@
});
}
- final shortGets = keyShorter.shortKeys(entry.value.getKeys);
- final shortPuts = keyShorter.shortKeys(entry.value.putKeys);
+ final cycleData = cycleToPrint.data;
+ final shortGets = keyShorter.shortKeys(cycleData.getKeys);
+ final shortPuts = keyShorter.shortKeys(cycleData.putKeys);
_writelnWithIndent('get: $shortGets');
_writelnWithIndent('put: $shortPuts');
});
@@ -228,7 +245,14 @@
}
void _writeUriList(String name, Iterable<Uri> uriIterable) {
- final uriStrList = uriIterable.map((uri) => '$uri').toList();
+ final uriStrList = <String>[];
+ for (final uri in uriIterable) {
+ if (omitSdkFiles && uri.isScheme('dart')) {
+ continue;
+ }
+ uriStrList.add('$uri');
+ }
+
if (uriStrList.isNotEmpty) {
uriStrList.sort();
_writelnWithIndent(name);
@@ -270,11 +294,9 @@
}
}
-extension<K, V> on Iterable<MapEntry<K, V>> {
- Iterable<MapEntry<K2, V>> mapKey<K2>(K2 Function(K key) convertKey) {
- return map((e) {
- final newKey = convertKey(e.key);
- return MapEntry(newKey, e.value);
- });
- }
+class _LibraryCycleToPrint {
+ final String pathListStr;
+ final LibraryCycleTestData data;
+
+ _LibraryCycleToPrint(this.pathListStr, this.data);
}
diff --git a/pkg/analyzer/test/src/dart/micro/file_resolution.dart b/pkg/analyzer/test/src/dart/micro/file_resolution.dart
index 9e72754..85fcdfd 100644
--- a/pkg/analyzer/test/src/dart/micro/file_resolution.dart
+++ b/pkg/analyzer/test/src/dart/micro/file_resolution.dart
@@ -67,13 +67,17 @@
newFile(_testFile, content);
}
- void assertStateString(String expected) {
+ void assertStateString(
+ String expected, {
+ bool omitSdkFiles = true,
+ }) {
final buffer = StringBuffer();
printer.AnalyzerStatePrinter(
byteStore: byteStore,
fileStateIdProvider: _fileStateIdProvider,
keyShorter: _keyShorter,
libraryContext: libraryContext,
+ omitSdkFiles: omitSdkFiles,
resourceProvider: resourceProvider,
sink: buffer,
).writeFileResolver(testData);
diff --git a/pkg/analyzer/test/src/dart/micro/simple_file_resolver_test.dart b/pkg/analyzer/test/src/dart/micro/simple_file_resolver_test.dart
index 8b247dd..a65c96b 100644
--- a/pkg/analyzer/test/src/dart/micro/simple_file_resolver_test.dart
+++ b/pkg/analyzer/test/src/dart/micro/simple_file_resolver_test.dart
@@ -47,102 +47,51 @@
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/test/lib/a.dart
current
id: file_0
kind: library
unlinkedKey: k00
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
+ uri: package:dart.test/a.dart
+ /workspace/dart/test/lib/b.dart
current
id: file_1
kind: library
unlinkedKey: k01
unlinkedGet: []
unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/test/lib/a.dart
- current
- id: file_5
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05]
- uri: package:dart.test/a.dart
- /workspace/dart/test/lib/b.dart
- current
- id: file_6
- kind: library
- unlinkedKey: k06
- unlinkedGet: []
- unlinkedPut: [k06]
uri: package:dart.test/b.dart
/workspace/dart/test/lib/c.dart
current
- id: file_7
+ id: file_2
kind: library
- unlinkedKey: k07
+ unlinkedKey: k02
unlinkedGet: []
- unlinkedPut: [k07]
+ unlinkedPut: [k02]
uri: package:dart.test/c.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k08
- libraries: file_0 file_1 file_3 file_4
- get: []
- put: [k08]
/workspace/dart/test/lib/a.dart
current
- key: k09
- libraries: file_5
+ key: k03
+ libraries: file_0
get: []
- put: [k09]
+ put: [k03]
/workspace/dart/test/lib/b.dart
current
- key: k10
- libraries: file_6
+ key: k04
+ libraries: file_1
get: []
- put: [k10]
+ put: [k04]
/workspace/dart/test/lib/c.dart
current
- key: k11
- libraries: file_7
+ key: k05
+ libraries: file_2
get: []
- put: [k11]
+ put: [k05]
elementFactory
hasElement
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.test/a.dart
package:dart.test/b.dart
package:dart.test/c.dart
@@ -154,102 +103,51 @@
await resolveFile(c.path);
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/test/lib/a.dart
current
id: file_0
kind: library
unlinkedKey: k00
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
+ uri: package:dart.test/a.dart
+ /workspace/dart/test/lib/b.dart
current
id: file_1
kind: library
unlinkedKey: k01
unlinkedGet: []
unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/test/lib/a.dart
- current
- id: file_5
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05]
- uri: package:dart.test/a.dart
- /workspace/dart/test/lib/b.dart
- current
- id: file_6
- kind: library
- unlinkedKey: k06
- unlinkedGet: []
- unlinkedPut: [k06]
uri: package:dart.test/b.dart
/workspace/dart/test/lib/c.dart
current
- id: file_7
+ id: file_2
kind: library
- unlinkedKey: k07
+ unlinkedKey: k02
unlinkedGet: []
- unlinkedPut: [k07]
+ unlinkedPut: [k02]
uri: package:dart.test/c.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k08
- libraries: file_0 file_1 file_3 file_4
- get: []
- put: [k08]
/workspace/dart/test/lib/a.dart
current
- key: k09
- libraries: file_5
+ key: k03
+ libraries: file_0
get: []
- put: [k09]
+ put: [k03]
/workspace/dart/test/lib/b.dart
current
- key: k10
- libraries: file_6
+ key: k04
+ libraries: file_1
get: []
- put: [k10]
+ put: [k04]
/workspace/dart/test/lib/c.dart
current
- key: k11
- libraries: file_7
+ key: k05
+ libraries: file_2
get: []
- put: [k11]
+ put: [k05]
elementFactory
hasElement
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.test/a.dart
package:dart.test/b.dart
package:dart.test/c.dart
@@ -261,102 +159,51 @@
await resolveFile(a.path);
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/test/lib/a.dart
current
id: file_0
kind: library
unlinkedKey: k00
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
+ uri: package:dart.test/a.dart
+ /workspace/dart/test/lib/b.dart
current
id: file_1
kind: library
unlinkedKey: k01
unlinkedGet: []
unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/test/lib/a.dart
- current
- id: file_5
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05]
- uri: package:dart.test/a.dart
- /workspace/dart/test/lib/b.dart
- current
- id: file_6
- kind: library
- unlinkedKey: k06
- unlinkedGet: []
- unlinkedPut: [k06]
uri: package:dart.test/b.dart
/workspace/dart/test/lib/c.dart
current
- id: file_7
+ id: file_2
kind: library
- unlinkedKey: k07
+ unlinkedKey: k02
unlinkedGet: []
- unlinkedPut: [k07]
+ unlinkedPut: [k02]
uri: package:dart.test/c.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k08
- libraries: file_0 file_1 file_3 file_4
- get: []
- put: [k08]
/workspace/dart/test/lib/a.dart
current
- key: k09
- libraries: file_5
+ key: k03
+ libraries: file_0
get: []
- put: [k09]
+ put: [k03]
/workspace/dart/test/lib/b.dart
current
- key: k10
- libraries: file_6
+ key: k04
+ libraries: file_1
get: []
- put: [k10]
+ put: [k04]
/workspace/dart/test/lib/c.dart
current
- key: k11
- libraries: file_7
+ key: k05
+ libraries: file_2
get: []
- put: [k11]
+ put: [k05]
elementFactory
hasElement
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.test/a.dart
package:dart.test/b.dart
package:dart.test/c.dart
@@ -368,193 +215,91 @@
fileResolver.changeFiles([a.path]);
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
- current
- id: file_0
- kind: library
- unlinkedKey: k00
+ /workspace/dart/test/lib/a.dart
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
+ uri: package:dart.test/a.dart
+ /workspace/dart/test/lib/b.dart
current
id: file_1
kind: library
unlinkedKey: k01
unlinkedGet: []
unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/test/lib/a.dart
- unlinkedGet: []
- unlinkedPut: [k05]
- uri: package:dart.test/a.dart
- /workspace/dart/test/lib/b.dart
- current
- id: file_6
- kind: library
- unlinkedKey: k06
- unlinkedGet: []
- unlinkedPut: [k06]
uri: package:dart.test/b.dart
/workspace/dart/test/lib/c.dart
unlinkedGet: []
- unlinkedPut: [k07]
+ unlinkedPut: [k02]
uri: package:dart.test/c.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k08
- libraries: file_0 file_1 file_3 file_4
- get: []
- put: [k08]
/workspace/dart/test/lib/a.dart
get: []
- put: [k09]
+ put: [k03]
/workspace/dart/test/lib/b.dart
current
- key: k10
- libraries: file_6
+ key: k04
+ libraries: file_1
get: []
- put: [k10]
+ put: [k04]
/workspace/dart/test/lib/c.dart
get: []
- put: [k11]
+ put: [k05]
elementFactory
hasElement
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.test/b.dart
byteStore
- 1: [k00, k01, k02, k03, k04, k06, k08, k10]
+ 1: [k01, k04, k06, k07, k08, k09, k10, k11]
''');
// Resolve, read again a.dart and c.dart
await resolveFile(c.path);
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/test/lib/a.dart
current
- id: file_0
+ id: file_3
kind: library
unlinkedKey: k00
unlinkedGet: []
- unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
+ unlinkedPut: [k00, k00]
+ uri: package:dart.test/a.dart
+ /workspace/dart/test/lib/b.dart
current
id: file_1
kind: library
unlinkedKey: k01
unlinkedGet: []
unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/test/lib/a.dart
- current
- id: file_8
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05, k05]
- uri: package:dart.test/a.dart
- /workspace/dart/test/lib/b.dart
- current
- id: file_6
- kind: library
- unlinkedKey: k06
- unlinkedGet: []
- unlinkedPut: [k06]
uri: package:dart.test/b.dart
/workspace/dart/test/lib/c.dart
current
- id: file_9
+ id: file_4
kind: library
- unlinkedKey: k07
+ unlinkedKey: k02
unlinkedGet: []
- unlinkedPut: [k07, k07]
+ unlinkedPut: [k02, k02]
uri: package:dart.test/c.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k08
- libraries: file_0 file_1 file_3 file_4
- get: []
- put: [k08]
/workspace/dart/test/lib/a.dart
current
- key: k09
- libraries: file_8
+ key: k03
+ libraries: file_3
get: []
- put: [k09, k09]
+ put: [k03, k03]
/workspace/dart/test/lib/b.dart
current
- key: k10
- libraries: file_6
+ key: k04
+ libraries: file_1
get: []
- put: [k10]
+ put: [k04]
/workspace/dart/test/lib/c.dart
current
- key: k11
- libraries: file_9
+ key: k05
+ libraries: file_4
get: []
- put: [k11, k11]
+ put: [k05, k05]
elementFactory
hasElement
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.test/a.dart
package:dart.test/b.dart
package:dart.test/c.dart
@@ -681,83 +426,32 @@
await resolveFile(b.path);
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/test/lib/a.dart
current
id: file_0
kind: library
unlinkedKey: k00
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
- current
- id: file_1
- kind: library
- unlinkedKey: k01
- unlinkedGet: []
- unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/test/lib/a.dart
- current
- id: file_5
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05]
uri: package:dart.test/a.dart
/workspace/dart/test/lib/b.dart
current
- id: file_6
+ id: file_1
kind: partOfUriKnown
- library: file_5
- unlinkedKey: k06
+ library: file_0
+ unlinkedKey: k01
unlinkedGet: []
- unlinkedPut: [k06]
+ unlinkedPut: [k01]
uri: package:dart.test/b.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k07
- libraries: file_0 file_1 file_3 file_4
- get: []
- put: [k07]
/workspace/dart/test/lib/a.dart
current
- key: k08
- libraries: file_5
+ key: k02
+ libraries: file_0
get: []
- put: [k08]
+ put: [k02]
elementFactory
hasElement
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.test/a.dart
byteStore
1: [k00, k01, k02, k03, k04, k05, k06, k07, k08]
@@ -767,156 +461,53 @@
fileResolver.changeFiles([b.path]);
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
- current
- id: file_0
- kind: library
- unlinkedKey: k00
- unlinkedGet: []
- unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
- current
- id: file_1
- kind: library
- unlinkedKey: k01
- unlinkedGet: []
- unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
/workspace/dart/test/lib/a.dart
unlinkedGet: []
- unlinkedPut: [k05]
+ unlinkedPut: [k00]
uri: package:dart.test/a.dart
/workspace/dart/test/lib/b.dart
unlinkedGet: []
- unlinkedPut: [k06]
+ unlinkedPut: [k01]
uri: package:dart.test/b.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k07
- libraries: file_0 file_1 file_3 file_4
- get: []
- put: [k07]
/workspace/dart/test/lib/a.dart
get: []
- put: [k08]
+ put: [k02]
elementFactory
- hasElement
- dart:_internal
- dart:async
- dart:core
- dart:math
byteStore
- 1: [k00, k01, k02, k03, k04, k07]
+ 1: [k03, k04, k05, k06, k07, k08]
''');
// Resolve, read a.dart and b.dart
await resolveFile(b.path);
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/test/lib/a.dart
current
- id: file_0
+ id: file_2
kind: library
unlinkedKey: k00
unlinkedGet: []
- unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
- current
- id: file_1
- kind: library
- unlinkedKey: k01
- unlinkedGet: []
- unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/test/lib/a.dart
- current
- id: file_7
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05, k05]
+ unlinkedPut: [k00, k00]
uri: package:dart.test/a.dart
/workspace/dart/test/lib/b.dart
current
- id: file_8
+ id: file_3
kind: partOfUriKnown
- library: file_7
- unlinkedKey: k06
+ library: file_2
+ unlinkedKey: k01
unlinkedGet: []
- unlinkedPut: [k06, k06]
+ unlinkedPut: [k01, k01]
uri: package:dart.test/b.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k07
- libraries: file_0 file_1 file_3 file_4
- get: []
- put: [k07]
/workspace/dart/test/lib/a.dart
current
- key: k08
- libraries: file_7
+ key: k02
+ libraries: file_2
get: []
- put: [k08, k08]
+ put: [k02, k02]
elementFactory
hasElement
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.test/a.dart
byteStore
1: [k00, k01, k02, k03, k04, k05, k06, k07, k08]
@@ -943,97 +534,46 @@
await resolveFile(c.path);
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/test/lib/a.dart
current
id: file_0
kind: library
unlinkedKey: k00
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
- current
- id: file_1
- kind: library
- unlinkedKey: k01
- unlinkedGet: []
- unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/test/lib/a.dart
- current
- id: file_5
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05]
uri: package:dart.test/a.dart
/workspace/dart/test/lib/b.dart
current
- id: file_6
+ id: file_1
kind: partOfUriKnown
- library: file_5
- unlinkedKey: k06
+ library: file_0
+ unlinkedKey: k01
unlinkedGet: []
- unlinkedPut: [k06]
+ unlinkedPut: [k01]
uri: package:dart.test/b.dart
/workspace/dart/test/lib/c.dart
current
- id: file_7
+ id: file_2
kind: library
- unlinkedKey: k07
+ unlinkedKey: k02
unlinkedGet: []
- unlinkedPut: [k07]
+ unlinkedPut: [k02]
uri: package:dart.test/c.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k08
- libraries: file_0 file_1 file_3 file_4
- get: []
- put: [k08]
/workspace/dart/test/lib/a.dart
current
- key: k09
- libraries: file_5
+ key: k03
+ libraries: file_0
get: []
- put: [k09]
+ put: [k03]
/workspace/dart/test/lib/c.dart
current
- key: k10
- libraries: file_7
+ key: k04
+ libraries: file_2
get: []
- put: [k10]
+ put: [k04]
elementFactory
hasElement
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.test/a.dart
package:dart.test/c.dart
byteStore
@@ -1044,177 +584,74 @@
fileResolver.changeFiles([b.path]);
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
- current
- id: file_0
- kind: library
- unlinkedKey: k00
- unlinkedGet: []
- unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
- current
- id: file_1
- kind: library
- unlinkedKey: k01
- unlinkedGet: []
- unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
/workspace/dart/test/lib/a.dart
unlinkedGet: []
- unlinkedPut: [k05]
+ unlinkedPut: [k00]
uri: package:dart.test/a.dart
/workspace/dart/test/lib/b.dart
unlinkedGet: []
- unlinkedPut: [k06]
+ unlinkedPut: [k01]
uri: package:dart.test/b.dart
/workspace/dart/test/lib/c.dart
unlinkedGet: []
- unlinkedPut: [k07]
+ unlinkedPut: [k02]
uri: package:dart.test/c.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k08
- libraries: file_0 file_1 file_3 file_4
- get: []
- put: [k08]
/workspace/dart/test/lib/a.dart
get: []
- put: [k09]
+ put: [k03]
/workspace/dart/test/lib/c.dart
get: []
- put: [k10]
+ put: [k04]
elementFactory
- hasElement
- dart:_internal
- dart:async
- dart:core
- dart:math
byteStore
- 1: [k00, k01, k02, k03, k04, k08]
+ 1: [k05, k06, k07, k08, k09, k10]
''');
// Read again a.dart, b.dart, c.dart
await resolveFile(c.path);
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
- current
- id: file_0
- kind: library
- unlinkedKey: k00
- unlinkedGet: []
- unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
- current
- id: file_1
- kind: library
- unlinkedKey: k01
- unlinkedGet: []
- unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
+ /workspace/dart/test/lib/a.dart
current
id: file_3
kind: library
- unlinkedKey: k03
+ unlinkedKey: k00
unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/test/lib/a.dart
- current
- id: file_8
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05, k05]
+ unlinkedPut: [k00, k00]
uri: package:dart.test/a.dart
/workspace/dart/test/lib/b.dart
current
- id: file_9
+ id: file_4
kind: partOfUriKnown
- library: file_8
- unlinkedKey: k06
+ library: file_3
+ unlinkedKey: k01
unlinkedGet: []
- unlinkedPut: [k06, k06]
+ unlinkedPut: [k01, k01]
uri: package:dart.test/b.dart
/workspace/dart/test/lib/c.dart
current
- id: file_10
+ id: file_5
kind: library
- unlinkedKey: k07
+ unlinkedKey: k02
unlinkedGet: []
- unlinkedPut: [k07, k07]
+ unlinkedPut: [k02, k02]
uri: package:dart.test/c.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k08
- libraries: file_0 file_1 file_3 file_4
- get: []
- put: [k08]
/workspace/dart/test/lib/a.dart
current
- key: k09
- libraries: file_8
+ key: k03
+ libraries: file_3
get: []
- put: [k09, k09]
+ put: [k03, k03]
/workspace/dart/test/lib/c.dart
current
- key: k10
- libraries: file_10
+ key: k04
+ libraries: file_5
get: []
- put: [k10, k10]
+ put: [k04, k04]
elementFactory
hasElement
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.test/a.dart
package:dart.test/c.dart
byteStore
@@ -1342,74 +779,23 @@
await resolveFile(a.path);
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/test/lib/a.dart
current
id: file_0
kind: library
unlinkedKey: k00
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
- current
- id: file_1
- kind: library
- unlinkedKey: k01
- unlinkedGet: []
- unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/test/lib/a.dart
- current
- id: file_5
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05]
uri: package:dart.test/a.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k06
- libraries: file_0 file_1 file_3 file_4
- get: []
- put: [k06]
/workspace/dart/test/lib/a.dart
current
- key: k07
- libraries: file_5
+ key: k01
+ libraries: file_0
get: []
- put: [k07]
+ put: [k01]
elementFactory
hasElement
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.test/a.dart
byteStore
1: [k00, k01, k02, k03, k04, k05, k06, k07]
@@ -1421,37 +807,14 @@
// The byte store is empty - no unlinked or linked data.
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/test/lib/a.dart
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
- unlinkedGet: []
- unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/test/lib/a.dart
- unlinkedGet: []
- unlinkedPut: [k05]
uri: package:dart.test/a.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- get: []
- put: [k06]
/workspace/dart/test/lib/a.dart
get: []
- put: [k07]
+ put: [k01]
elementFactory
byteStore
''');
@@ -1953,77 +1316,23 @@
await fileResolver.linkLibraries2(path: a.path);
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/test/lib/a.dart
current
id: file_0
kind: library
unlinkedKey: k00
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
- current
- id: file_1
- kind: library
- unlinkedKey: k01
- unlinkedGet: []
- unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/test/lib/a.dart
- current
- id: file_5
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05]
uri: package:dart.test/a.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k06
- libraries: file_0 file_1 file_3 file_4
- get: [k06]
- put: [k06]
/workspace/dart/test/lib/a.dart
current
- key: k07
- libraries: file_5
- get: [k07]
- put: [k07]
+ key: k01
+ libraries: file_0
+ get: [k01]
+ put: [k01]
elementFactory
- hasElement
- dart:async
- dart:core
hasReader
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.test/a.dart
byteStore
1: [k00, k01, k02, k03, k04, k05, k06, k07]
@@ -2034,78 +1343,25 @@
);
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/test/lib/a.dart
current
id: file_0
kind: library
unlinkedKey: k00
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
- current
- id: file_1
- kind: library
- unlinkedKey: k01
- unlinkedGet: []
- unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/test/lib/a.dart
- current
- id: file_5
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05]
uri: package:dart.test/a.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k06
- libraries: file_0 file_1 file_3 file_4
- get: [k06]
- put: [k06]
/workspace/dart/test/lib/a.dart
current
- key: k07
- libraries: file_5
- get: [k07]
- put: [k07]
+ key: k01
+ libraries: file_0
+ get: [k01]
+ put: [k01]
elementFactory
hasElement
- dart:async
- dart:core
package:dart.test/a.dart
hasReader
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.test/a.dart
byteStore
1: [k00, k01, k02, k03, k04, k05, k06, k07]
@@ -2118,91 +1374,37 @@
// The reference count for each data is exactly `1`.
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/test/lib/a.dart
current
id: file_0
kind: library
unlinkedKey: k00
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
- current
- id: file_1
- kind: library
- unlinkedKey: k01
- unlinkedGet: []
- unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/test/lib/a.dart
- current
- id: file_5
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05]
uri: package:dart.test/a.dart
/workspace/dart/test/lib/b.dart
current
- id: file_6
+ id: file_1
kind: library
unlinkedKey: k08
unlinkedGet: []
unlinkedPut: [k08]
uri: package:dart.test/b.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k06
- libraries: file_0 file_1 file_3 file_4
- get: [k06, k06]
- put: [k06]
/workspace/dart/test/lib/a.dart
current
- key: k07
- libraries: file_5
- get: [k07, k07]
- put: [k07]
+ key: k01
+ libraries: file_0
+ get: [k01, k01]
+ put: [k01]
/workspace/dart/test/lib/b.dart
current
key: k09
- libraries: file_6
+ libraries: file_1
get: [k09]
put: [k09]
elementFactory
- hasElement
- dart:async
- dart:core
hasReader
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.test/a.dart
package:dart.test/b.dart
byteStore
@@ -2223,92 +1425,39 @@
// read a.dart to access them, so we keep it as a reader.
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/test/lib/a.dart
current
id: file_0
kind: library
unlinkedKey: k00
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
- current
- id: file_1
- kind: library
- unlinkedKey: k01
- unlinkedGet: []
- unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/test/lib/a.dart
- current
- id: file_5
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05]
uri: package:dart.test/a.dart
/workspace/dart/test/lib/b.dart
current
- id: file_6
+ id: file_1
kind: library
unlinkedKey: k08
unlinkedGet: []
unlinkedPut: [k08]
uri: package:dart.test/b.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k06
- libraries: file_0 file_1 file_3 file_4
- get: [k06, k06]
- put: [k06]
/workspace/dart/test/lib/a.dart
current
- key: k07
- libraries: file_5
- get: [k07, k07]
- put: [k07]
+ key: k01
+ libraries: file_0
+ get: [k01, k01]
+ put: [k01]
/workspace/dart/test/lib/b.dart
current
key: k09
- libraries: file_6
+ libraries: file_1
get: [k09]
put: [k09]
elementFactory
hasElement
- dart:async
- dart:core
package:dart.test/b.dart
hasReader
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.test/a.dart
package:dart.test/b.dart
byteStore
@@ -2331,77 +1480,23 @@
// The reference count for each data is exactly `1`.
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/test/lib/test.dart
current
id: file_0
kind: library
unlinkedKey: k00
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
- current
- id: file_1
- kind: library
- unlinkedKey: k01
- unlinkedGet: []
- unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/test/lib/test.dart
- current
- id: file_5
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05]
uri: package:dart.test/test.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k06
- libraries: file_0 file_1 file_3 file_4
- get: [k06]
- put: [k06]
/workspace/dart/test/lib/test.dart
current
- key: k07
- libraries: file_5
- get: [k07]
- put: [k07]
+ key: k01
+ libraries: file_0
+ get: [k01]
+ put: [k01]
elementFactory
- hasElement
- dart:async
- dart:core
hasReader
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.test/test.dart
byteStore
1: [k00, k01, k02, k03, k04, k05, k06, k07]
@@ -2418,79 +1513,25 @@
// We created the library element for the test file, using the reader.
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/test/lib/test.dart
current
id: file_0
kind: library
unlinkedKey: k00
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
- current
- id: file_1
- kind: library
- unlinkedKey: k01
- unlinkedGet: []
- unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/test/lib/test.dart
- current
- id: file_5
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05]
uri: package:dart.test/test.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k06
- libraries: file_0 file_1 file_3 file_4
- get: [k06]
- put: [k06]
/workspace/dart/test/lib/test.dart
current
- key: k07
- libraries: file_5
- get: [k07]
- put: [k07]
+ key: k01
+ libraries: file_0
+ get: [k01]
+ put: [k01]
elementFactory
hasElement
- dart:_internal
- dart:async
- dart:core
package:dart.test/test.dart
hasReader
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.test/test.dart
byteStore
1: [k00, k01, k02, k03, k04, k05, k06, k07]
@@ -2610,102 +1651,51 @@
await resolveFile(c.path);
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/aaa/lib/a.dart
current
id: file_0
kind: library
unlinkedKey: k00
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
+ uri: package:dart.aaa/a.dart
+ /workspace/dart/aaa/lib/b.dart
current
id: file_1
kind: library
unlinkedKey: k01
unlinkedGet: []
unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/aaa/lib/a.dart
- current
- id: file_5
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05]
- uri: package:dart.aaa/a.dart
- /workspace/dart/aaa/lib/b.dart
- current
- id: file_6
- kind: library
- unlinkedKey: k06
- unlinkedGet: []
- unlinkedPut: [k06]
uri: package:dart.aaa/b.dart
/workspace/dart/aaa/lib/c.dart
current
- id: file_7
+ id: file_2
kind: library
- unlinkedKey: k07
+ unlinkedKey: k02
unlinkedGet: []
- unlinkedPut: [k07]
+ unlinkedPut: [k02]
uri: package:dart.aaa/c.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k08
- libraries: file_0 file_1 file_3 file_4
- get: []
- put: [k08]
/workspace/dart/aaa/lib/a.dart
current
- key: k09
- libraries: file_5
+ key: k03
+ libraries: file_0
get: []
- put: [k09]
+ put: [k03]
/workspace/dart/aaa/lib/b.dart
current
- key: k10
- libraries: file_6
+ key: k04
+ libraries: file_1
get: []
- put: [k10]
+ put: [k04]
/workspace/dart/aaa/lib/c.dart
current
- key: k11
- libraries: file_7
+ key: k05
+ libraries: file_2
get: []
- put: [k11]
+ put: [k05]
elementFactory
hasElement
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.aaa/a.dart
package:dart.aaa/b.dart
package:dart.aaa/c.dart
@@ -2718,99 +1708,48 @@
// No data for b.dart anymore.
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/aaa/lib/a.dart
current
id: file_0
kind: library
unlinkedKey: k00
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
- current
- id: file_1
- kind: library
- unlinkedKey: k01
- unlinkedGet: []
- unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/aaa/lib/a.dart
- current
- id: file_5
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05]
uri: package:dart.aaa/a.dart
/workspace/dart/aaa/lib/b.dart
unlinkedGet: []
- unlinkedPut: [k06]
+ unlinkedPut: [k01]
uri: package:dart.aaa/b.dart
/workspace/dart/aaa/lib/c.dart
current
- id: file_7
+ id: file_2
kind: library
- unlinkedKey: k07
+ unlinkedKey: k02
unlinkedGet: []
- unlinkedPut: [k07]
+ unlinkedPut: [k02]
uri: package:dart.aaa/c.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k08
- libraries: file_0 file_1 file_3 file_4
- get: []
- put: [k08]
/workspace/dart/aaa/lib/a.dart
current
- key: k09
- libraries: file_5
+ key: k03
+ libraries: file_0
get: []
- put: [k09]
+ put: [k03]
/workspace/dart/aaa/lib/b.dart
get: []
- put: [k10]
+ put: [k04]
/workspace/dart/aaa/lib/c.dart
current
- key: k11
- libraries: file_7
+ key: k05
+ libraries: file_2
get: []
- put: [k11]
+ put: [k05]
elementFactory
hasElement
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.aaa/a.dart
package:dart.aaa/c.dart
byteStore
- 1: [k00, k01, k02, k03, k04, k05, k07, k08, k09, k11]
+ 1: [k00, k02, k03, k05, k06, k07, k08, k09, k10, k11]
''');
}
@@ -2845,144 +1784,93 @@
await resolveFile(f.path);
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/aaa/lib/a.dart
current
id: file_0
kind: library
unlinkedKey: k00
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
+ uri: package:dart.aaa/a.dart
+ /workspace/dart/aaa/lib/b.dart
current
id: file_1
kind: library
unlinkedKey: k01
unlinkedGet: []
unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
+ uri: package:dart.aaa/b.dart
+ /workspace/dart/aaa/lib/c.dart
current
id: file_2
- kind: partOfName
- library: file_1
+ kind: library
unlinkedKey: k02
unlinkedGet: []
unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
+ uri: package:dart.aaa/c.dart
+ /workspace/dart/aaa/lib/d.dart
current
id: file_3
kind: library
unlinkedKey: k03
unlinkedGet: []
unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
+ uri: package:dart.aaa/d.dart
+ /workspace/dart/aaa/lib/e.dart
current
id: file_4
kind: library
unlinkedKey: k04
unlinkedGet: []
unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/aaa/lib/a.dart
+ uri: package:dart.aaa/e.dart
+ /workspace/dart/aaa/lib/f.dart
current
id: file_5
kind: library
unlinkedKey: k05
unlinkedGet: []
unlinkedPut: [k05]
- uri: package:dart.aaa/a.dart
- /workspace/dart/aaa/lib/b.dart
- current
- id: file_6
- kind: library
- unlinkedKey: k06
- unlinkedGet: []
- unlinkedPut: [k06]
- uri: package:dart.aaa/b.dart
- /workspace/dart/aaa/lib/c.dart
- current
- id: file_7
- kind: library
- unlinkedKey: k07
- unlinkedGet: []
- unlinkedPut: [k07]
- uri: package:dart.aaa/c.dart
- /workspace/dart/aaa/lib/d.dart
- current
- id: file_8
- kind: library
- unlinkedKey: k08
- unlinkedGet: []
- unlinkedPut: [k08]
- uri: package:dart.aaa/d.dart
- /workspace/dart/aaa/lib/e.dart
- current
- id: file_9
- kind: library
- unlinkedKey: k09
- unlinkedGet: []
- unlinkedPut: [k09]
- uri: package:dart.aaa/e.dart
- /workspace/dart/aaa/lib/f.dart
- current
- id: file_10
- kind: library
- unlinkedKey: k10
- unlinkedGet: []
- unlinkedPut: [k10]
uri: package:dart.aaa/f.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k11
- libraries: file_0 file_1 file_3 file_4
- get: []
- put: [k11]
/workspace/dart/aaa/lib/a.dart
current
- key: k12
- libraries: file_5
+ key: k06
+ libraries: file_0
get: []
- put: [k12]
+ put: [k06]
/workspace/dart/aaa/lib/b.dart
current
- key: k13
- libraries: file_6
+ key: k07
+ libraries: file_1
get: []
- put: [k13]
+ put: [k07]
/workspace/dart/aaa/lib/c.dart
current
- key: k14
- libraries: file_7
+ key: k08
+ libraries: file_2
get: []
- put: [k14]
+ put: [k08]
/workspace/dart/aaa/lib/d.dart
current
- key: k15
- libraries: file_8
+ key: k09
+ libraries: file_3
get: []
- put: [k15]
+ put: [k09]
/workspace/dart/aaa/lib/e.dart
current
- key: k16
- libraries: file_9
+ key: k10
+ libraries: file_4
get: []
- put: [k16]
+ put: [k10]
/workspace/dart/aaa/lib/f.dart
current
- key: k17
- libraries: file_10
+ key: k11
+ libraries: file_5
get: []
- put: [k17]
+ put: [k11]
elementFactory
hasElement
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.aaa/a.dart
package:dart.aaa/b.dart
package:dart.aaa/c.dart
@@ -2997,136 +1885,85 @@
// No data for b.dart and e.dart anymore.
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/aaa/lib/a.dart
current
id: file_0
kind: library
unlinkedKey: k00
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
- current
- id: file_1
- kind: library
- unlinkedKey: k01
+ uri: package:dart.aaa/a.dart
+ /workspace/dart/aaa/lib/b.dart
unlinkedGet: []
unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
+ uri: package:dart.aaa/b.dart
+ /workspace/dart/aaa/lib/c.dart
current
id: file_2
- kind: partOfName
- library: file_1
+ kind: library
unlinkedKey: k02
unlinkedGet: []
unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
+ uri: package:dart.aaa/c.dart
+ /workspace/dart/aaa/lib/d.dart
current
id: file_3
kind: library
unlinkedKey: k03
unlinkedGet: []
unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
+ uri: package:dart.aaa/d.dart
+ /workspace/dart/aaa/lib/e.dart
unlinkedGet: []
unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/aaa/lib/a.dart
+ uri: package:dart.aaa/e.dart
+ /workspace/dart/aaa/lib/f.dart
current
id: file_5
kind: library
unlinkedKey: k05
unlinkedGet: []
unlinkedPut: [k05]
- uri: package:dart.aaa/a.dart
- /workspace/dart/aaa/lib/b.dart
- unlinkedGet: []
- unlinkedPut: [k06]
- uri: package:dart.aaa/b.dart
- /workspace/dart/aaa/lib/c.dart
- current
- id: file_7
- kind: library
- unlinkedKey: k07
- unlinkedGet: []
- unlinkedPut: [k07]
- uri: package:dart.aaa/c.dart
- /workspace/dart/aaa/lib/d.dart
- current
- id: file_8
- kind: library
- unlinkedKey: k08
- unlinkedGet: []
- unlinkedPut: [k08]
- uri: package:dart.aaa/d.dart
- /workspace/dart/aaa/lib/e.dart
- unlinkedGet: []
- unlinkedPut: [k09]
- uri: package:dart.aaa/e.dart
- /workspace/dart/aaa/lib/f.dart
- current
- id: file_10
- kind: library
- unlinkedKey: k10
- unlinkedGet: []
- unlinkedPut: [k10]
uri: package:dart.aaa/f.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k11
- libraries: file_0 file_1 file_3 file_4
- get: []
- put: [k11]
/workspace/dart/aaa/lib/a.dart
current
- key: k12
- libraries: file_5
+ key: k06
+ libraries: file_0
get: []
- put: [k12]
+ put: [k06]
/workspace/dart/aaa/lib/b.dart
get: []
- put: [k13]
+ put: [k07]
/workspace/dart/aaa/lib/c.dart
current
- key: k14
- libraries: file_7
+ key: k08
+ libraries: file_2
get: []
- put: [k14]
+ put: [k08]
/workspace/dart/aaa/lib/d.dart
current
- key: k15
- libraries: file_8
+ key: k09
+ libraries: file_3
get: []
- put: [k15]
+ put: [k09]
/workspace/dart/aaa/lib/e.dart
get: []
- put: [k16]
+ put: [k10]
/workspace/dart/aaa/lib/f.dart
current
- key: k17
- libraries: file_10
+ key: k11
+ libraries: file_5
get: []
- put: [k17]
+ put: [k11]
elementFactory
hasElement
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.aaa/a.dart
package:dart.aaa/c.dart
package:dart.aaa/d.dart
package:dart.aaa/f.dart
byteStore
- 1: [k00, k01, k02, k03, k04, k05, k07, k08, k10, k11, k12, k14, k15, k17]
+ 1: [k00, k02, k03, k05, k06, k08, k09, k11, k12, k13, k14, k15, k16, k17]
''');
}
@@ -3143,74 +1980,23 @@
// No b.dart anywhere.
assertStateString(r'''
files
- /sdk/lib/_internal/internal.dart
+ /workspace/dart/aaa/lib/a.dart
current
id: file_0
kind: library
unlinkedKey: k00
unlinkedGet: []
unlinkedPut: [k00]
- uri: dart:_internal
- /sdk/lib/async/async.dart
- current
- id: file_1
- kind: library
- unlinkedKey: k01
- unlinkedGet: []
- unlinkedPut: [k01]
- uri: dart:async
- /sdk/lib/async/stream.dart
- current
- id: file_2
- kind: partOfName
- library: file_1
- unlinkedKey: k02
- unlinkedGet: []
- unlinkedPut: [k02]
- uri: dart:async/stream.dart
- /sdk/lib/core/core.dart
- current
- id: file_3
- kind: library
- unlinkedKey: k03
- unlinkedGet: []
- unlinkedPut: [k03]
- uri: dart:core
- /sdk/lib/math/math.dart
- current
- id: file_4
- kind: library
- unlinkedKey: k04
- unlinkedGet: []
- unlinkedPut: [k04]
- uri: dart:math
- /workspace/dart/aaa/lib/a.dart
- current
- id: file_5
- kind: library
- unlinkedKey: k05
- unlinkedGet: []
- unlinkedPut: [k05]
uri: package:dart.aaa/a.dart
libraryCycles
- /sdk/lib/_internal/internal.dart /sdk/lib/async/async.dart /sdk/lib/core/core.dart /sdk/lib/math/math.dart
- current
- key: k06
- libraries: file_0 file_1 file_3 file_4
- get: []
- put: [k06]
/workspace/dart/aaa/lib/a.dart
current
- key: k07
- libraries: file_5
+ key: k01
+ libraries: file_0
get: []
- put: [k07]
+ put: [k01]
elementFactory
hasElement
- dart:_internal
- dart:async
- dart:core
- dart:math
package:dart.aaa/a.dart
byteStore
1: [k00, k01, k02, k03, k04, k05, k06, k07]
diff --git a/pkg/analyzer/test/src/dart/resolution/context_collection_resolution.dart b/pkg/analyzer/test/src/dart/resolution/context_collection_resolution.dart
index 3c8bd3b..a32ceaf 100644
--- a/pkg/analyzer/test/src/dart/resolution/context_collection_resolution.dart
+++ b/pkg/analyzer/test/src/dart/resolution/context_collection_resolution.dart
@@ -167,7 +167,11 @@
expect(workspace, TypeMatcher<BazelWorkspace>());
}
- void assertDriverStateString(File file, String expected) {
+ void assertDriverStateString(
+ File file,
+ String expected, {
+ bool omitSdkFiles = true,
+ }) {
final analysisDriver = driverFor(file.path);
final buffer = StringBuffer();
@@ -176,6 +180,7 @@
fileStateIdProvider: _fileStateIdProvider,
keyShorter: _keyShorter,
libraryContext: analysisDriver.libraryContext,
+ omitSdkFiles: omitSdkFiles,
resourceProvider: resourceProvider,
sink: buffer,
).writeAnalysisDriver(analysisDriver.testView!);
diff --git a/pkg/compiler/lib/src/closure.dart b/pkg/compiler/lib/src/closure.dart
index e5bd068..5afa5db 100644
--- a/pkg/compiler/lib/src/closure.dart
+++ b/pkg/compiler/lib/src/closure.dart
@@ -9,7 +9,7 @@
import 'elements/entities.dart';
import 'js_model/closure.dart';
import 'js_model/element_map.dart';
-import 'serialization/serialization.dart';
+import 'serialization/serialization_interfaces.dart';
/// Class that provides information for how closures are rewritten/represented
/// to preserve Dart semantics when compiled to JavaScript. Given a particular
@@ -289,7 +289,6 @@
/// Returns the [local] for which [field] was created.
Local getLocalForField(KernelToLocalsMap localsMap, FieldEntity field) {
failedAt(field, "No local for $field.");
- return null;
}
/// Convenience pointer to the field entity representation in the closure
diff --git a/pkg/compiler/lib/src/common/codegen.dart b/pkg/compiler/lib/src/common/codegen.dart
index 1d64607..67f0c30 100644
--- a/pkg/compiler/lib/src/common/codegen.dart
+++ b/pkg/compiler/lib/src/common/codegen.dart
@@ -28,7 +28,7 @@
import '../js_model/elements.dart' show JGeneratorBody;
import '../js_model/type_recipe.dart' show TypeRecipe;
import '../native/behavior.dart';
-import '../serialization/serialization.dart';
+import '../serialization/serialization_interfaces.dart';
import '../ssa/ssa.dart';
import '../universe/feature.dart';
import '../universe/selector.dart';
diff --git a/pkg/compiler/lib/src/diagnostics/invariant.dart b/pkg/compiler/lib/src/diagnostics/invariant.dart
index 76cdea1..10fecc4 100644
--- a/pkg/compiler/lib/src/diagnostics/invariant.dart
+++ b/pkg/compiler/lib/src/diagnostics/invariant.dart
@@ -35,10 +35,6 @@
///
/// failedAt(position, message);
///
-/// or, if the enclosing function requires a result or control flow:
-///
-/// throw failedAt(position, message);
-///
-bool failedAt(Spannable spannable, [String? message]) {
+Never failedAt(Spannable spannable, [String? message]) {
throw SpannableAssertionFailure(spannable, message);
}
diff --git a/pkg/compiler/lib/src/inferrer/builder.dart b/pkg/compiler/lib/src/inferrer/builder.dart
index f5d9729..01f4f58 100644
--- a/pkg/compiler/lib/src/inferrer/builder.dart
+++ b/pkg/compiler/lib/src/inferrer/builder.dart
@@ -1868,7 +1868,6 @@
}
failedAt(CURRENT_ELEMENT_SPANNABLE,
"Unexpected logical operator '${node.operatorEnum}'.");
- return null;
}
@override
diff --git a/pkg/compiler/lib/src/inferrer/engine.dart b/pkg/compiler/lib/src/inferrer/engine.dart
index 997d067..58d80d5 100644
--- a/pkg/compiler/lib/src/inferrer/engine.dart
+++ b/pkg/compiler/lib/src/inferrer/engine.dart
@@ -544,7 +544,6 @@
break;
}
failedAt(member, 'Unexpected member definition: $definition.');
- return null;
}
/// Returns the `call` method on [cls] or the `noSuchMethod` if [cls] doesn't
diff --git a/pkg/compiler/lib/src/inferrer/types.dart b/pkg/compiler/lib/src/inferrer/types.dart
index 8705fb2..c36483f 100644
--- a/pkg/compiler/lib/src/inferrer/types.dart
+++ b/pkg/compiler/lib/src/inferrer/types.dart
@@ -20,7 +20,7 @@
import '../js_model/js_world.dart';
import '../js_model/locals.dart';
import '../serialization/deferrable.dart';
-import '../serialization/serialization.dart';
+import '../serialization/serialization_interfaces.dart';
import '../universe/selector.dart' show Selector;
import '../world.dart' show JClosedWorld;
import 'abstract_value_domain.dart';
diff --git a/pkg/compiler/lib/src/ir/modular.dart b/pkg/compiler/lib/src/ir/modular.dart
index 4713bbe..956a0e0 100644
--- a/pkg/compiler/lib/src/ir/modular.dart
+++ b/pkg/compiler/lib/src/ir/modular.dart
@@ -17,7 +17,7 @@
import '../ir/static_type.dart';
import '../js_backend/annotations.dart';
import '../kernel/element_map.dart';
-import '../serialization/serialization.dart';
+import '../serialization/serialization_interfaces.dart';
import '../util/enumset.dart';
import 'annotations.dart';
import 'impact.dart';
diff --git a/pkg/compiler/lib/src/js_backend/type_reference.dart b/pkg/compiler/lib/src/js_backend/type_reference.dart
index 2f4bc25..5bfc9ef 100644
--- a/pkg/compiler/lib/src/js_backend/type_reference.dart
+++ b/pkg/compiler/lib/src/js_backend/type_reference.dart
@@ -76,7 +76,7 @@
TypeExpressionRecipe,
SingletonTypeEnvironmentRecipe,
FullTypeEnvironmentRecipe;
-import '../serialization/serialization.dart';
+import '../serialization/serialization_interfaces.dart';
import '../util/util.dart' show Hashing;
import 'frequency_assignment.dart';
import 'namer.dart';
diff --git a/pkg/compiler/lib/src/js_model/closure.dart b/pkg/compiler/lib/src/js_model/closure.dart
index 23de9f0..cbde6f5 100644
--- a/pkg/compiler/lib/src/js_model/closure.dart
+++ b/pkg/compiler/lib/src/js_model/closure.dart
@@ -20,7 +20,7 @@
import '../js_model/env.dart';
import '../ordered_typeset.dart';
import '../serialization/deferrable.dart';
-import '../serialization/serialization.dart';
+import '../serialization/serialization_interfaces.dart';
import '../universe/selector.dart';
import 'elements.dart';
import 'jrecord_field_interface.dart';
diff --git a/pkg/compiler/lib/src/js_model/element_map.dart b/pkg/compiler/lib/src/js_model/element_map.dart
index 7ec2a72..d939160 100644
--- a/pkg/compiler/lib/src/js_model/element_map.dart
+++ b/pkg/compiler/lib/src/js_model/element_map.dart
@@ -21,7 +21,7 @@
import '../js_model/elements.dart' show JGeneratorBody;
import '../native/behavior.dart';
import '../serialization/deferrable.dart';
-import '../serialization/serialization.dart';
+import '../serialization/serialization_interfaces.dart';
import '../universe/call_structure.dart';
import '../universe/selector.dart';
import '../world.dart';
diff --git a/pkg/compiler/lib/src/js_model/element_map_impl.dart b/pkg/compiler/lib/src/js_model/element_map_impl.dart
index a1a18b5..492f593 100644
--- a/pkg/compiler/lib/src/js_model/element_map_impl.dart
+++ b/pkg/compiler/lib/src/js_model/element_map_impl.dart
@@ -46,7 +46,7 @@
import '../native/behavior.dart';
import '../options.dart';
import '../ordered_typeset.dart';
-import '../serialization/serialization.dart';
+import '../serialization/serialization_interfaces.dart';
import '../universe/call_structure.dart';
import '../universe/member_usage.dart';
import '../universe/selector.dart';
diff --git a/pkg/compiler/lib/src/js_model/elements.dart b/pkg/compiler/lib/src/js_model/elements.dart
index 915558b..b318237 100644
--- a/pkg/compiler/lib/src/js_model/elements.dart
+++ b/pkg/compiler/lib/src/js_model/elements.dart
@@ -11,7 +11,7 @@
import '../elements/indexed.dart';
import '../elements/names.dart';
import '../elements/types.dart';
-import '../serialization/serialization.dart';
+import '../serialization/serialization_interfaces.dart';
import '../universe/class_set.dart' show ClassHierarchyNodesMapKey;
import 'closure.dart';
diff --git a/pkg/compiler/lib/src/js_model/env.dart b/pkg/compiler/lib/src/js_model/env.dart
index 0bf7e80..e1e7e2d 100644
--- a/pkg/compiler/lib/src/js_model/env.dart
+++ b/pkg/compiler/lib/src/js_model/env.dart
@@ -18,7 +18,7 @@
import '../js_model/class_type_variable_access.dart';
import '../ordered_typeset.dart';
import '../serialization/deferrable.dart';
-import '../serialization/serialization.dart';
+import '../serialization/serialization_interfaces.dart';
import 'closure.dart';
import 'element_map.dart';
import 'element_map_impl.dart';
diff --git a/pkg/compiler/lib/src/js_model/js_world.dart b/pkg/compiler/lib/src/js_model/js_world.dart
index afdce46..92361b3 100644
--- a/pkg/compiler/lib/src/js_model/js_world.dart
+++ b/pkg/compiler/lib/src/js_model/js_world.dart
@@ -30,7 +30,7 @@
import '../js_backend/runtime_types_resolution.dart';
import '../ordered_typeset.dart';
import '../options.dart';
-import '../serialization/serialization.dart';
+import '../serialization/serialization_interfaces.dart';
import '../universe/class_hierarchy.dart';
import '../universe/class_set.dart';
import '../universe/function_set.dart' show FunctionSet;
diff --git a/pkg/compiler/lib/src/js_model/type_recipe.dart b/pkg/compiler/lib/src/js_model/type_recipe.dart
index 5a31add..ad26ddc 100644
--- a/pkg/compiler/lib/src/js_model/type_recipe.dart
+++ b/pkg/compiler/lib/src/js_model/type_recipe.dart
@@ -359,7 +359,6 @@
}
failedAt(CURRENT_ELEMENT_SPANNABLE,
'Expected a TypeExpressionRecipe: $environmentRecipe');
- return null;
}
if (environmentStructure is FullTypeEnvironmentStructure) {
@@ -390,7 +389,6 @@
failedAt(CURRENT_ELEMENT_SPANNABLE,
'Unknown environmentStructure: $environmentStructure');
- return null;
}
@override
@@ -429,7 +427,6 @@
failedAt(CURRENT_ELEMENT_SPANNABLE,
'unexpected bind on environment with structure $environmentStructure');
- return null;
}
@override
@@ -526,7 +523,6 @@
}
failedAt(CURRENT_ELEMENT_SPANNABLE, 'Unexpected recipe: $recipe');
- return null;
}
DartType _substituteType(DartType type) => visit(type, null);
diff --git a/pkg/compiler/lib/src/kernel/element_map_impl.dart b/pkg/compiler/lib/src/kernel/element_map_impl.dart
index 0fb9528..2a75105 100644
--- a/pkg/compiler/lib/src/kernel/element_map_impl.dart
+++ b/pkg/compiler/lib/src/kernel/element_map_impl.dart
@@ -56,13 +56,15 @@
import '../universe/world_impact.dart';
import 'element_map.dart';
+import 'element_map_interfaces.dart' show KernelToElementMapForClassHierarchy;
import 'env.dart';
import 'kelements.dart';
import 'kernel_impact.dart';
/// Implementation of [IrToElementMap] that only supports world
/// impact computation.
-class KernelToElementMap implements IrToElementMap {
+class KernelToElementMap
+ implements KernelToElementMapForClassHierarchy, IrToElementMap {
final CompilerOptions options;
@override
final DiagnosticReporter reporter;
@@ -276,6 +278,7 @@
}
/// Returns the superclass of [cls] if any.
+ @override
ClassEntity getSuperClass(ClassEntity cls) {
return getSuperType(cls)?.element;
}
@@ -704,6 +707,7 @@
// class A {}
// class B = Object with A;
// class C = Object with B;
+ @override
ClassEntity getAppliedMixin(IndexedClass cls) {
assert(checkFamily(cls));
KClassData data = classes.getData(cls);
@@ -799,6 +803,7 @@
}
/// Returns all supertypes of [cls].
+ @override
Iterable<InterfaceType> getSuperTypes(ClassEntity cls) {
return getOrderedTypeSet(cls).supertypes;
}
@@ -1583,6 +1588,7 @@
/// Returns `true` if [cls] implements `Function` either explicitly or through
/// a `call` method.
+ @override
bool implementsFunction(IndexedClass cls) {
assert(checkFamily(cls));
KClassData data = classes.getData(cls);
diff --git a/pkg/compiler/lib/src/kernel/element_map_interfaces.dart b/pkg/compiler/lib/src/kernel/element_map_interfaces.dart
new file mode 100644
index 0000000..ef733f02
--- /dev/null
+++ b/pkg/compiler/lib/src/kernel/element_map_interfaces.dart
@@ -0,0 +1,15 @@
+// Copyright (c) 2022, 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 '../elements/entities.dart' show ClassEntity;
+import '../elements/indexed.dart' show IndexedClass;
+import '../elements/types.dart' show InterfaceType;
+
+abstract class KernelToElementMapForClassHierarchy {
+ ClassEntity? getSuperClass(ClassEntity cls);
+ int getHierarchyDepth(IndexedClass cls);
+ Iterable<InterfaceType> getSuperTypes(ClassEntity cls);
+ ClassEntity? getAppliedMixin(IndexedClass cls);
+ bool implementsFunction(IndexedClass cls);
+}
diff --git a/pkg/compiler/lib/src/native/resolver.dart b/pkg/compiler/lib/src/native/resolver.dart
index c445602..bf52762 100644
--- a/pkg/compiler/lib/src/native/resolver.dart
+++ b/pkg/compiler/lib/src/native/resolver.dart
@@ -130,7 +130,6 @@
if (fields.length != 1) {
failedAt(spannable,
'Annotations needs one string: ${value.toStructuredText(dartTypes)}');
- return null;
}
final field = fields.single;
if (field is StringConstantValue) {
@@ -140,7 +139,6 @@
} else {
failedAt(spannable,
'Annotations needs one string: ${value.toStructuredText(dartTypes)}');
- return null;
}
}
return null;
diff --git a/pkg/compiler/lib/src/serialization/serialization.dart b/pkg/compiler/lib/src/serialization/serialization.dart
index e15e038..f772db2 100644
--- a/pkg/compiler/lib/src/serialization/serialization.dart
+++ b/pkg/compiler/lib/src/serialization/serialization.dart
@@ -29,7 +29,15 @@
import 'deferrable.dart';
import 'member_data.dart';
import 'serialization_interfaces.dart' as migrated
- show DataSourceReader, DataSinkWriter;
+ show
+ CodegenReader,
+ CodegenWriter,
+ DataSourceReader,
+ DataSinkWriter,
+ EntityLookup,
+ EntityReader,
+ EntityWriter,
+ LocalLookup;
import 'indexed_sink_source.dart';
import 'tags.dart';
@@ -39,6 +47,8 @@
export 'object_sink.dart';
export 'object_source.dart';
export 'tags.dart';
+export 'serialization_interfaces.dart'
+ show CodegenReader, EntityLookup, EntityReader, EntityWriter;
part 'sink.dart';
part 'source.dart';
@@ -85,86 +95,3 @@
DataSourceIndices(this.previousSourceReader);
}
-
-/// Interface used for looking up entities by index during deserialization.
-abstract class EntityLookup {
- /// Returns the indexed library corresponding to [index].
- IndexedLibrary getLibraryByIndex(int index);
-
- /// Returns the indexed class corresponding to [index].
- IndexedClass getClassByIndex(int index);
-
- /// Returns the indexed member corresponding to [index].
- IndexedMember getMemberByIndex(int index);
-
- /// Returns the indexed type variable corresponding to [index].
- IndexedTypeVariable getTypeVariableByIndex(int index);
-}
-
-/// Decoding strategy for entity references.
-class EntityReader {
- const EntityReader();
-
- IndexedLibrary readLibraryFromDataSource(
- DataSourceReader source, EntityLookup entityLookup) {
- return entityLookup.getLibraryByIndex(source.readInt());
- }
-
- IndexedClass readClassFromDataSource(
- DataSourceReader source, EntityLookup entityLookup) {
- return entityLookup.getClassByIndex(source.readInt());
- }
-
- IndexedMember readMemberFromDataSource(
- DataSourceReader source, EntityLookup entityLookup) {
- return entityLookup.getMemberByIndex(source.readInt());
- }
-
- IndexedTypeVariable readTypeVariableFromDataSource(
- DataSourceReader source, EntityLookup entityLookup) {
- return entityLookup.getTypeVariableByIndex(source.readInt());
- }
-}
-
-/// Encoding strategy for entity references.
-class EntityWriter {
- const EntityWriter();
-
- void writeLibraryToDataSink(DataSinkWriter sink, IndexedLibrary value) {
- sink.writeInt(value.libraryIndex);
- }
-
- void writeClassToDataSink(DataSinkWriter sink, IndexedClass value) {
- sink.writeInt(value.classIndex);
- }
-
- void writeMemberToDataSink(DataSinkWriter sink, IndexedMember value) {
- sink.writeInt(value.memberIndex);
- }
-
- void writeTypeVariableToDataSink(
- DataSinkWriter sink, IndexedTypeVariable value) {
- sink.writeInt(value.typeVariableIndex);
- }
-}
-
-/// Interface used for looking up locals by index during deserialization.
-abstract class LocalLookup {
- Local getLocalByIndex(MemberEntity memberContext, int index);
-}
-
-/// Interface used for reading codegen only data during deserialization.
-abstract class CodegenReader {
- AbstractValue readAbstractValue(DataSourceReader source);
- OutputUnit readOutputUnitReference(DataSourceReader source);
- js.Node readJsNode(DataSourceReader source);
- TypeRecipe readTypeRecipe(DataSourceReader source);
-}
-
-/// Interface used for writing codegen only data during serialization.
-abstract class CodegenWriter {
- void writeAbstractValue(DataSinkWriter sink, AbstractValue value);
- void writeOutputUnitReference(DataSinkWriter sink, OutputUnit value);
- void writeJsNode(DataSinkWriter sink, js.Node node);
- void writeTypeRecipe(DataSinkWriter sink, TypeRecipe recipe);
-}
diff --git a/pkg/compiler/lib/src/serialization/serialization_interfaces.dart b/pkg/compiler/lib/src/serialization/serialization_interfaces.dart
index 9f36a86..72b1c1aa 100644
--- a/pkg/compiler/lib/src/serialization/serialization_interfaces.dart
+++ b/pkg/compiler/lib/src/serialization/serialization_interfaces.dart
@@ -3,14 +3,29 @@
// BSD-style license that can be found in the LICENSE file.
import 'package:kernel/ast.dart' as ir
- show DartType, LibraryDependency, Member, Name, TreeNode;
+ show
+ Class,
+ DartType,
+ Library,
+ LibraryDependency,
+ Member,
+ Name,
+ TreeNode,
+ TypeParameter;
+import '../common.dart';
import '../constants/values.dart' show ConstantValue;
+import '../deferred_load/output_unit.dart';
import '../elements/entities.dart';
+import '../elements/indexed.dart';
import '../elements/types.dart' show DartType;
import '../inferrer/abstract_value_domain.dart' show AbstractValue;
-
+import '../js/js.dart' as js;
+import '../js_model/type_recipe.dart';
import 'deferrable.dart';
+import 'member_data.dart' show ComponentLookup;
+
+export 'member_data.dart' show ComponentLookup;
export 'tags.dart';
abstract class StringInterner {
@@ -62,6 +77,9 @@
void writeTreeNode(ir.TreeNode value);
void writeTreeNodeOrNull(ir.TreeNode value);
void writeTreeNodes(Iterable<ir.TreeNode>? values, {bool allowNull = false});
+ void writeTreeNodeMap<V>(Map<ir.TreeNode, V> map, void f(V value));
+
+ void writeClassNode(ir.Class value);
// TODO(48820): 'covariant ClassEntity' is used below because the
// implementation takes IndexedClass. What this means is that in pre-NNBD
@@ -97,6 +115,10 @@
void writeLibraryMap<V>(Map<LibraryEntity, V>? map, void f(V value),
{bool allowNull = false});
+ void writeLibraryNode(ir.Library value);
+
+ void writeTypeRecipe(TypeRecipe value);
+
void writeDartTypeNode(ir.DartType value);
void writeDartTypeNodeOrNull(ir.DartType? value);
void writeDartTypeNodes(Iterable<ir.DartType>? values,
@@ -107,6 +129,12 @@
void writeDartTypesOrNull(Iterable<DartType>? values);
void writeDartTypes(Iterable<DartType> values);
+ void writeTypeParameterNode(ir.TypeParameter value);
+ void writeTypeParameterNodes(Iterable<ir.TypeParameter> values);
+
+ void writeTypeVariableMap<V>(
+ Map<IndexedTypeVariable, V> map, void f(V value));
+
void inMemberContext(ir.Member context, void f());
void writeTreeNodeMapInContext<V>(Map<ir.TreeNode, V>? map, void f(V value),
{bool allowNull = false});
@@ -126,6 +154,9 @@
void writeDoubleValue(double value);
void writeIntegerValue(int value);
+ void writeLocalOrNull(Local? local);
+ void writeLocalMap<V>(Map<Local, V> map, void f(V value));
+
void writeImport(ImportEntity import);
void writeImportOrNull(ImportEntity? import);
void writeImports(Iterable<ImportEntity>? values, {bool allowNull = false});
@@ -134,6 +165,10 @@
void writeAbstractValue(AbstractValue value);
+ void writeJsNodeOrNull(js.Node? value);
+
+ void writeSourceSpan(SourceSpan value);
+
void writeDeferrable(void f());
}
@@ -143,6 +178,11 @@
int get startOffset;
int get endOffset;
+ void registerComponentLookup(ComponentLookup componentLookup);
+ void registerLocalLookup(LocalLookup localLookup);
+ void registerEntityLookup(EntityLookup entityLookup);
+ void registerEntityReader(EntityReader reader);
+
void begin(String tag);
void end(String tag);
@@ -170,6 +210,10 @@
ir.TreeNode? readTreeNodeOrNull();
List<E> readTreeNodes<E extends ir.TreeNode>();
List<E>? readTreeNodesOrNull<E extends ir.TreeNode>();
+ Map<K, V> readTreeNodeMap<K extends ir.TreeNode, V>(V f());
+ Map<K, V> readTreeNodeMapOrNull<K extends ir.TreeNode, V>(V f());
+
+ ir.Class readClassNode();
ClassEntity readClass(); // IndexedClass
ClassEntity? readClassOrNull(); // IndexedClass
@@ -193,6 +237,10 @@
Map<K, V> readLibraryMap<K extends LibraryEntity, V>(V f());
Map<K, V>? readLibraryMapOrNull<K extends LibraryEntity, V>(V f());
+ ir.Library readLibraryNode();
+
+ TypeRecipe readTypeRecipe();
+
ir.DartType readDartTypeNode();
ir.DartType? readDartTypeNodeOrNull();
List<ir.DartType> readDartTypeNodes();
@@ -203,6 +251,11 @@
List<DartType> readDartTypes();
List<DartType>? readDartTypesOrNull();
+ Map<K, V> readTypeVariableMap<K extends IndexedTypeVariable, V>(V f());
+
+ ir.TypeParameter readTypeParameterNode();
+ List<ir.TypeParameter> readTypeParameterNodes();
+
T inMemberContext<T>(ir.Member context, T f());
Map<K, V> readTreeNodeMapInContext<K extends ir.TreeNode, V>(V f());
Map<K, V>? readTreeNodeMapInContextOrNull<K extends ir.TreeNode, V>(V f());
@@ -232,7 +285,97 @@
AbstractValue readAbstractValue();
+ js.Node? readJsNodeOrNull();
+
+ SourceSpan readSourceSpan();
+
+ Local? readLocalOrNull();
+ Map<K, V> readLocalMap<K extends Local, V>(V f());
+
E readWithSource<E>(DataSourceReader source, E f());
E readWithOffset<E>(int offset, E f());
Deferrable<E> readDeferrable<E>(E f(), {bool cacheData = true});
}
+
+/// Interface used for looking up locals by index during deserialization.
+abstract class LocalLookup {
+ Local getLocalByIndex(MemberEntity memberContext, int index);
+}
+
+/// Interface used for reading codegen only data during deserialization.
+abstract class CodegenReader {
+ AbstractValue readAbstractValue(DataSourceReader source);
+ OutputUnit readOutputUnitReference(DataSourceReader source);
+ js.Node readJsNode(DataSourceReader source);
+ TypeRecipe readTypeRecipe(DataSourceReader source);
+}
+
+/// Interface used for writing codegen only data during serialization.
+abstract class CodegenWriter {
+ void writeAbstractValue(DataSinkWriter sink, AbstractValue value);
+ void writeOutputUnitReference(DataSinkWriter sink, OutputUnit value);
+ void writeJsNode(DataSinkWriter sink, js.Node node);
+ void writeTypeRecipe(DataSinkWriter sink, TypeRecipe recipe);
+}
+
+/// Interface used for looking up entities by index during deserialization.
+abstract class EntityLookup {
+ /// Returns the indexed library corresponding to [index].
+ IndexedLibrary getLibraryByIndex(int index);
+
+ /// Returns the indexed class corresponding to [index].
+ IndexedClass getClassByIndex(int index);
+
+ /// Returns the indexed member corresponding to [index].
+ IndexedMember getMemberByIndex(int index);
+
+ /// Returns the indexed type variable corresponding to [index].
+ IndexedTypeVariable getTypeVariableByIndex(int index);
+}
+
+/// Decoding strategy for entity references.
+class EntityReader {
+ const EntityReader();
+
+ IndexedLibrary readLibraryFromDataSource(
+ DataSourceReader source, EntityLookup entityLookup) {
+ return entityLookup.getLibraryByIndex(source.readInt());
+ }
+
+ IndexedClass readClassFromDataSource(
+ DataSourceReader source, EntityLookup entityLookup) {
+ return entityLookup.getClassByIndex(source.readInt());
+ }
+
+ IndexedMember readMemberFromDataSource(
+ DataSourceReader source, EntityLookup entityLookup) {
+ return entityLookup.getMemberByIndex(source.readInt());
+ }
+
+ IndexedTypeVariable readTypeVariableFromDataSource(
+ DataSourceReader source, EntityLookup entityLookup) {
+ return entityLookup.getTypeVariableByIndex(source.readInt());
+ }
+}
+
+/// Encoding strategy for entity references.
+class EntityWriter {
+ const EntityWriter();
+
+ void writeLibraryToDataSink(DataSinkWriter sink, IndexedLibrary value) {
+ sink.writeInt(value.libraryIndex);
+ }
+
+ void writeClassToDataSink(DataSinkWriter sink, IndexedClass value) {
+ sink.writeInt(value.classIndex);
+ }
+
+ void writeMemberToDataSink(DataSinkWriter sink, IndexedMember value) {
+ sink.writeInt(value.memberIndex);
+ }
+
+ void writeTypeVariableToDataSink(
+ DataSinkWriter sink, IndexedTypeVariable value) {
+ sink.writeInt(value.typeVariableIndex);
+ }
+}
diff --git a/pkg/compiler/lib/src/serialization/sink.dart b/pkg/compiler/lib/src/serialization/sink.dart
index dd92d56..71397c6 100644
--- a/pkg/compiler/lib/src/serialization/sink.dart
+++ b/pkg/compiler/lib/src/serialization/sink.dart
@@ -42,8 +42,8 @@
final Map<Type, IndexedSink> _generalCaches = {};
- EntityWriter _entityWriter = const EntityWriter();
- CodegenWriter _codegenWriter;
+ migrated.EntityWriter _entityWriter = const migrated.EntityWriter();
+ migrated.CodegenWriter _codegenWriter;
final Map<String, int> tagFrequencyMap;
@@ -308,6 +308,7 @@
}
/// Writes a reference to the kernel library node [value] to this data sink.
+ @override
void writeLibraryNode(ir.Library value) {
_writeDataKind(DataKind.libraryNode);
_writeLibraryNode(value);
@@ -318,6 +319,7 @@
}
/// Writes a reference to the kernel class node [value] to this data sink.
+ @override
void writeClassNode(ir.Class value) {
_writeDataKind(DataKind.classNode);
_writeClassNode(value);
@@ -504,18 +506,13 @@
///
/// This is a convenience method to be used together with
/// [DataSourceReader.readTreeNodeMap].
- void writeTreeNodeMap<V>(Map<ir.TreeNode, V> map, void f(V value),
- {bool allowNull = false}) {
- if (map == null) {
- assert(allowNull);
- writeInt(0);
- } else {
- writeInt(map.length);
- map.forEach((ir.TreeNode key, V value) {
- writeTreeNode(key);
- f(value);
- });
- }
+ @override
+ void writeTreeNodeMap<V>(Map<ir.TreeNode, V> map, void f(V value)) {
+ writeInt(map.length);
+ map.forEach((ir.TreeNode key, V value) {
+ writeTreeNode(key);
+ f(value);
+ });
}
/// Writes a reference to the kernel tree node [value] in the known [context]
@@ -585,6 +582,7 @@
/// Writes a reference to the kernel type parameter node [value] to this data
/// sink.
+ @override
void writeTypeParameterNode(ir.TypeParameter value) {
_writeDataKind(DataKind.typeParameterNode);
_writeTypeParameter(value, null);
@@ -612,16 +610,11 @@
///
/// This is a convenience method to be used together with
/// [DataSourceReader.readTypeParameterNodes].
- void writeTypeParameterNodes(Iterable<ir.TypeParameter> values,
- {bool allowNull = false}) {
- if (values == null) {
- assert(allowNull);
- writeInt(0);
- } else {
- writeInt(values.length);
- for (ir.TypeParameter value in values) {
- writeTypeParameterNode(value);
- }
+ @override
+ void writeTypeParameterNodes(Iterable<ir.TypeParameter> values) {
+ writeInt(values.length);
+ for (ir.TypeParameter value in values) {
+ writeTypeParameterNode(value);
}
}
@@ -716,6 +709,7 @@
}
/// Writes the source span [value] to this data sink.
+ @override
void writeSourceSpan(SourceSpan value) {
_writeDataKind(DataKind.sourceSpan);
_writeUri(value.uri);
@@ -892,18 +886,14 @@
///
/// This is a convenience method to be used together with
/// [DataSourceReader.readTypeVariableMap].
- void writeTypeVariableMap<V>(Map<IndexedTypeVariable, V> map, void f(V value),
- {bool allowNull = false}) {
- if (map == null) {
- assert(allowNull);
- writeInt(0);
- } else {
- writeInt(map.length);
- map.forEach((IndexedTypeVariable key, V value) {
- writeTypeVariable(key);
- f(value);
- });
- }
+ @override
+ void writeTypeVariableMap<V>(
+ Map<IndexedTypeVariable, V> map, void f(V value)) {
+ writeInt(map.length);
+ map.forEach((IndexedTypeVariable key, V value) {
+ writeTypeVariable(key);
+ f(value);
+ });
}
/// Writes a reference to the local [value] to this data sink.
@@ -934,6 +924,7 @@
///
/// This is a convenience method to be used together with
/// [DataSourceReader.readLocalOrNull].
+ @override
void writeLocalOrNull(Local value) {
writeBool(value != null);
if (value != null) {
@@ -964,18 +955,13 @@
///
/// This is a convenience method to be used together with
/// [DataSourceReader.readLocalMap].
- void writeLocalMap<V>(Map<Local, V> map, void f(V value),
- {bool allowNull = false}) {
- if (map == null) {
- assert(allowNull);
- writeInt(0);
- } else {
- writeInt(map.length);
- map.forEach((Local key, V value) {
- writeLocal(key);
- f(value);
- });
- }
+ @override
+ void writeLocalMap<V>(Map<Local, V> map, void f(V value)) {
+ writeInt(map.length);
+ map.forEach((Local key, V value) {
+ writeLocal(key);
+ f(value);
+ });
}
/// Writes the constant [value] to this data sink.
@@ -1251,6 +1237,7 @@
/// Writes a potentially `null` js node [value] to this data sink.
///
/// This feature is only available a [CodegenWriter] has been registered.
+ @override
void writeJsNodeOrNull(js.Node value) {
writeBool(value != null);
if (value != null) {
@@ -1261,6 +1248,7 @@
/// Writes TypeRecipe [value] to this data sink.
///
/// This feature is only available a [CodegenWriter] has been registered.
+ @override
void writeTypeRecipe(TypeRecipe value) {
assert(_codegenWriter != null,
"Can not serialize a TypeRecipe without a registered codegen writer.");
@@ -1269,14 +1257,14 @@
/// Register an [EntityWriter] with this data sink for non-default encoding
/// of entity references.
- void registerEntityWriter(EntityWriter writer) {
+ void registerEntityWriter(migrated.EntityWriter writer) {
assert(writer != null);
_entityWriter = writer;
}
/// Register a [CodegenWriter] with this data sink to support serialization
/// of codegen only data.
- void registerCodegenWriter(CodegenWriter writer) {
+ void registerCodegenWriter(migrated.CodegenWriter writer) {
assert(writer != null);
assert(_codegenWriter == null);
_codegenWriter = writer;
diff --git a/pkg/compiler/lib/src/serialization/source.dart b/pkg/compiler/lib/src/serialization/source.dart
index e2d1e6b..14e4885 100644
--- a/pkg/compiler/lib/src/serialization/source.dart
+++ b/pkg/compiler/lib/src/serialization/source.dart
@@ -24,11 +24,11 @@
final bool useDataKinds;
final ValueInterner /*?*/ interner;
DataSourceIndices importedIndices;
- EntityReader _entityReader = const EntityReader();
+ migrated.EntityReader _entityReader = const migrated.EntityReader();
ComponentLookup _componentLookup;
- EntityLookup _entityLookup;
- LocalLookup _localLookup;
- CodegenReader _codegenReader;
+ migrated.EntityLookup _entityLookup;
+ migrated.LocalLookup _localLookup;
+ migrated.CodegenReader _codegenReader;
IndexedSource<String> _stringIndex;
IndexedSource<Uri> _uriIndex;
@@ -159,6 +159,7 @@
/// Registers a [ComponentLookup] object with this data source to support
/// deserialization of references to kernel nodes.
+ @override
void registerComponentLookup(ComponentLookup componentLookup) {
assert(_componentLookup == null);
_componentLookup = componentLookup;
@@ -171,45 +172,48 @@
/// Registers an [EntityLookup] object with this data source to support
/// deserialization of references to indexed entities.
- void registerEntityLookup(EntityLookup entityLookup) {
+ @override
+ void registerEntityLookup(migrated.EntityLookup entityLookup) {
assert(_entityLookup == null);
_entityLookup = entityLookup;
}
- EntityLookup get entityLookup {
+ migrated.EntityLookup get entityLookup {
assert(_entityLookup != null);
return _entityLookup /*!*/;
}
/// Registers an [EntityReader] with this data source for non-default encoding
/// of entity references.
- void registerEntityReader(EntityReader reader) {
+ @override
+ void registerEntityReader(migrated.EntityReader reader) {
assert(reader != null);
_entityReader = reader;
}
/// Registers a [LocalLookup] object with this data source to support
- void registerLocalLookup(LocalLookup localLookup) {
+ @override
+ void registerLocalLookup(migrated.LocalLookup localLookup) {
assert(_localLookup == null);
_localLookup = localLookup;
}
- LocalLookup get localLookup {
+ migrated.LocalLookup get localLookup {
assert(_localLookup != null);
return _localLookup /*!*/;
}
- /// Registers a [CodegenReader] with this data source to support
+ /// Registers a [migrated.CodegenReader] with this data source to support
/// deserialization of codegen only data.
- void registerCodegenReader(CodegenReader reader) {
+ void registerCodegenReader(migrated.CodegenReader reader) {
assert(reader != null);
assert(_codegenReader == null);
_codegenReader = reader;
}
- /// Unregisters the [CodegenReader] from this data source to remove support
+ /// Unregisters the [migrated.CodegenReader] from this data source to remove support
/// for deserialization of codegen only data.
- void deregisterCodegenReader(CodegenReader reader) {
+ void deregisterCodegenReader(migrated.CodegenReader reader) {
assert(_codegenReader == reader);
_codegenReader = null;
}
@@ -446,6 +450,7 @@
}
/// Reads a reference to a kernel library node from this data source.
+ @override
ir.Library readLibraryNode() {
_checkDataKind(DataKind.libraryNode);
return _readLibraryData().node;
@@ -457,6 +462,7 @@
}
/// Reads a reference to a kernel class node from this data source.
+ @override
ir.Class readClassNode() {
_checkDataKind(DataKind.classNode);
return _readClassData().node;
@@ -658,10 +664,15 @@
///
/// This is a convenience method to be used together with
/// [DataSinkWriter.writeTreeNodeMap].
- Map<K, V> readTreeNodeMap<K extends ir.TreeNode, V>(V f(),
- {bool emptyAsNull = false}) {
+ @override
+ Map<K, V> readTreeNodeMap<K extends ir.TreeNode, V>(V f()) {
+ return readTreeNodeMapOrNull(f) ?? <K, V>{};
+ }
+
+ @override
+ Map<K, V> readTreeNodeMapOrNull<K extends ir.TreeNode, V>(V f()) {
int count = readInt();
- if (count == 0 && emptyAsNull) return null;
+ if (count == 0) return null;
Map<K, V> map = {};
for (int i = 0; i < count; i++) {
ir.TreeNode node = readTreeNode();
@@ -742,6 +753,7 @@
}
/// Reads a reference to a kernel type parameter node from this data source.
+ @override
ir.TypeParameter readTypeParameterNode() {
_checkDataKind(DataKind.typeParameterNode);
return _readTypeParameter(null);
@@ -766,9 +778,9 @@
///
/// This is a convenience method to be used together with
/// [DataSinkWriter.writeTypeParameterNodes].
- List<ir.TypeParameter> readTypeParameterNodes({bool emptyAsNull = false}) {
+ @override
+ List<ir.TypeParameter> readTypeParameterNodes() {
int count = readInt();
- if (count == 0 && emptyAsNull) return null;
List<ir.TypeParameter> list = List<ir.TypeParameter>.filled(count, null);
for (int i = 0; i < count; i++) {
list[i] = readTypeParameterNode();
@@ -971,6 +983,7 @@
}
/// Reads a source span from this data source.
+ @override
SourceSpan readSourceSpan() {
_checkDataKind(DataKind.sourceSpan);
Uri uri = _readUri();
@@ -1183,10 +1196,9 @@
///
/// This is a convenience method to be used together with
/// [DataSinkWriter.writeTypeVariableMap].
- Map<K, V> readTypeVariableMap<K extends IndexedTypeVariable, V>(V f(),
- {bool emptyAsNull = false}) {
+ @override
+ Map<K, V> readTypeVariableMap<K extends IndexedTypeVariable, V>(V f()) {
int count = readInt();
- if (count == 0 && emptyAsNull) return null;
Map<K, V> map = {};
for (int i = 0; i < count; i++) {
IndexedTypeVariable node = readTypeVariable();
@@ -1221,6 +1233,7 @@
}
/// Reads a reference to a potentially `null` local from this data source.
+ @override
Local readLocalOrNull() {
bool hasValue = readBool();
if (hasValue) {
@@ -1251,10 +1264,9 @@
///
/// This is a convenience method to be used together with
/// [DataSinkWriter.writeLocalMap].
- Map<K, V> readLocalMap<K extends Local, V>(V f(),
- {bool emptyAsNull = false}) {
+ @override
+ Map<K, V> readLocalMap<K extends Local, V>(V f()) {
int count = readInt();
- if (count == 0 && emptyAsNull) return null;
Map<K, V> map = {};
for (int i = 0; i < count; i++) {
Local local = readLocal();
@@ -1550,6 +1562,7 @@
/// Reads a potentially `null` [js.Node] value from this data source.
///
/// This feature is only available a [CodegenReader] has been registered.
+ @override
js.Node readJsNodeOrNull() {
bool hasValue = readBool();
if (hasValue) {
@@ -1561,6 +1574,7 @@
/// Reads a [TypeRecipe] value from this data source.
///
/// This feature is only available a [CodegenReader] has been registered.
+ @override
TypeRecipe readTypeRecipe() {
assert(_codegenReader != null,
"Can not deserialize a TypeRecipe without a registered codegen reader.");
diff --git a/pkg/compiler/lib/src/universe/class_hierarchy.dart b/pkg/compiler/lib/src/universe/class_hierarchy.dart
index 80505f7..8634d09 100644
--- a/pkg/compiler/lib/src/universe/class_hierarchy.dart
+++ b/pkg/compiler/lib/src/universe/class_hierarchy.dart
@@ -2,13 +2,13 @@
// 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.
-// @dart = 2.10
-
import '../common.dart';
import '../common/elements.dart';
-import '../elements/entities.dart';
+import '../elements/entities.dart' show ClassEntity;
+import '../elements/indexed.dart' show IndexedClass;
import '../elements/types.dart' show InterfaceType;
-import '../kernel/element_map.dart' show KernelToElementMap;
+import '../kernel/element_map_interfaces.dart'
+ show KernelToElementMapForClassHierarchy;
import '../serialization/serialization_interfaces.dart';
import 'class_set.dart';
@@ -201,69 +201,66 @@
getClassHierarchyNode(_commonElements.objectClass);
node.forEachSubclass((ClassEntity cls) {
getClassHierarchyNode(cls).writeToDataSink(sink);
- return null;
+ return IterationStep.CONTINUE;
}, ClassHierarchyNode.ALL);
ClassSet set = getClassSet(_commonElements.objectClass);
set.forEachSubclass((ClassEntity cls) {
getClassSet(cls).writeToDataSink(sink);
- return null;
+ return IterationStep.CONTINUE;
}, ClassHierarchyNode.ALL);
sink.end(tag);
}
@override
bool isInstantiated(ClassEntity cls) {
- ClassHierarchyNode node = _classHierarchyNodes[cls];
+ ClassHierarchyNode? node = _classHierarchyNodes[cls];
return node != null && node.isInstantiated;
}
@override
bool isDirectlyInstantiated(ClassEntity cls) {
- ClassHierarchyNode node = _classHierarchyNodes[cls];
+ ClassHierarchyNode? node = _classHierarchyNodes[cls];
return node != null && node.isDirectlyInstantiated;
}
@override
bool isAbstractlyInstantiated(ClassEntity cls) {
- ClassHierarchyNode node = _classHierarchyNodes[cls];
+ ClassHierarchyNode? node = _classHierarchyNodes[cls];
return node != null && node.isAbstractlyInstantiated;
}
@override
bool isExplicitlyInstantiated(ClassEntity cls) {
- ClassHierarchyNode node = _classHierarchyNodes[cls];
+ ClassHierarchyNode? node = _classHierarchyNodes[cls];
return node != null && node.isExplicitlyInstantiated;
}
@override
bool isIndirectlyInstantiated(ClassEntity cls) {
- ClassHierarchyNode node = _classHierarchyNodes[cls];
+ ClassHierarchyNode? node = _classHierarchyNodes[cls];
return node != null && node.isIndirectlyInstantiated;
}
@override
bool isSubtypeOf(ClassEntity x, ClassEntity y) {
- ClassSet classSet = _classSets[y];
- assert(
- classSet != null,
+ ClassSet classSet = _classSets[y] ??
failedAt(
y,
"No ClassSet for $y (${y.runtimeType}): "
- "${dump(y)} : ${_classSets}"));
- ClassHierarchyNode classHierarchyNode = _classHierarchyNodes[x];
- assert(classHierarchyNode != null,
- failedAt(x, "No ClassHierarchyNode for $x: ${dump(x)}"));
+ "${dump(y)} : ${_classSets}");
+ ClassHierarchyNode classHierarchyNode = _classHierarchyNodes[x] ??
+ failedAt(x, "No ClassHierarchyNode for $x: ${dump(x)}");
return classSet.hasSubtype(classHierarchyNode);
}
@override
bool isSubclassOf(ClassEntity x, ClassEntity y) {
- return _classHierarchyNodes[y].hasSubclass(_classHierarchyNodes[x]);
+ return _classHierarchyNodes[y]!.hasSubclass(_classHierarchyNodes[x]!);
}
@override
Iterable<ClassEntity> subclassesOf(ClassEntity cls) {
- ClassHierarchyNode hierarchy = _classHierarchyNodes[cls];
+ ClassHierarchyNode? hierarchy = _classHierarchyNodes[cls];
if (hierarchy == null) return const [];
return hierarchy
.subclassesByMask(ClassHierarchyNode.EXPLICITLY_INSTANTIATED);
@@ -271,7 +268,7 @@
@override
Iterable<ClassEntity> strictSubclassesOf(ClassEntity cls) {
- ClassHierarchyNode subclasses = _classHierarchyNodes[cls];
+ ClassHierarchyNode? subclasses = _classHierarchyNodes[cls];
if (subclasses == null) return const [];
return subclasses.subclassesByMask(
ClassHierarchyNode.EXPLICITLY_INSTANTIATED,
@@ -280,7 +277,7 @@
@override
int strictSubclassCount(ClassEntity cls) {
- ClassHierarchyNode subclasses = _classHierarchyNodes[cls];
+ ClassHierarchyNode? subclasses = _classHierarchyNodes[cls];
if (subclasses == null) return 0;
return subclasses.instantiatedSubclassCount;
}
@@ -288,7 +285,7 @@
@override
void forEachStrictSubclassOf(
ClassEntity cls, IterationStep f(ClassEntity cls)) {
- ClassHierarchyNode subclasses = _classHierarchyNodes[cls];
+ ClassHierarchyNode? subclasses = _classHierarchyNodes[cls];
if (subclasses == null) return;
subclasses.forEachSubclass(f, ClassHierarchyNode.EXPLICITLY_INSTANTIATED,
strict: true);
@@ -296,7 +293,7 @@
@override
bool anyStrictSubclassOf(ClassEntity cls, bool predicate(ClassEntity cls)) {
- ClassHierarchyNode subclasses = _classHierarchyNodes[cls];
+ ClassHierarchyNode? subclasses = _classHierarchyNodes[cls];
if (subclasses == null) return false;
return subclasses.anySubclass(
predicate, ClassHierarchyNode.EXPLICITLY_INSTANTIATED,
@@ -305,7 +302,7 @@
@override
Iterable<ClassEntity> subtypesOf(ClassEntity cls) {
- ClassSet classSet = _classSets[cls];
+ ClassSet? classSet = _classSets[cls];
if (classSet == null) {
return const [];
} else {
@@ -316,7 +313,7 @@
@override
Iterable<ClassEntity> strictSubtypesOf(ClassEntity cls) {
- ClassSet classSet = _classSets[cls];
+ ClassSet? classSet = _classSets[cls];
if (classSet == null) {
return const [];
} else {
@@ -327,7 +324,7 @@
@override
Iterable<ClassEntity> allSubtypesOf(ClassEntity cls) {
- ClassSet classSet = _classSets[cls];
+ ClassSet? classSet = _classSets[cls];
if (classSet == null) {
return const [];
} else {
@@ -337,7 +334,7 @@
@override
int strictSubtypeCount(ClassEntity cls) {
- ClassSet classSet = _classSets[cls];
+ ClassSet? classSet = _classSets[cls];
if (classSet == null) return 0;
return classSet.instantiatedSubtypeCount;
}
@@ -345,7 +342,7 @@
@override
void forEachStrictSubtypeOf(
ClassEntity cls, IterationStep f(ClassEntity cls)) {
- ClassSet classSet = _classSets[cls];
+ ClassSet? classSet = _classSets[cls];
if (classSet == null) return;
classSet.forEachSubtype(f, ClassHierarchyNode.EXPLICITLY_INSTANTIATED,
strict: true);
@@ -353,7 +350,7 @@
@override
bool anyStrictSubtypeOf(ClassEntity cls, bool predicate(ClassEntity cls)) {
- ClassSet classSet = _classSets[cls];
+ ClassSet? classSet = _classSets[cls];
if (classSet == null) return false;
return classSet.anySubtype(
predicate, ClassHierarchyNode.EXPLICITLY_INSTANTIATED,
@@ -362,8 +359,8 @@
@override
bool haveAnyCommonSubtypes(ClassEntity a, ClassEntity b) {
- ClassSet classSetA = _classSets[a];
- ClassSet classSetB = _classSets[b];
+ ClassSet? classSetA = _classSets[a];
+ ClassSet? classSetB = _classSets[b];
if (classSetA == null || classSetB == null) return false;
// TODO(johnniwinther): Implement an optimized query on [ClassSet].
Set<ClassEntity> subtypesOfB = classSetB.subtypes().toSet();
@@ -377,7 +374,7 @@
@override
bool hasAnyStrictSubclass(ClassEntity cls) {
- ClassHierarchyNode subclasses = _classHierarchyNodes[cls];
+ ClassHierarchyNode? subclasses = _classHierarchyNodes[cls];
if (subclasses == null) return false;
return subclasses.isIndirectlyInstantiated;
}
@@ -391,7 +388,7 @@
bool hasOnlySubclasses(ClassEntity cls) {
// TODO(johnniwinther): move this to ClassSet?
if (cls == _commonElements.objectClass) return true;
- ClassSet classSet = _classSets[cls];
+ ClassSet? classSet = _classSets[cls];
if (classSet == null) {
// Vacuously true.
return true;
@@ -547,16 +544,16 @@
@override
ClassHierarchyNode getClassHierarchyNode(ClassEntity cls) {
- return _classHierarchyNodes[cls];
+ return _classHierarchyNodes[cls]!;
}
@override
ClassSet getClassSet(ClassEntity cls) {
- return _classSets[cls];
+ return _classSets[cls]!;
}
@override
- String dump([ClassEntity cls]) {
+ String dump([ClassEntity? cls]) {
StringBuffer sb = StringBuffer();
if (cls != null) {
sb.write("Classes in the closed world related to $cls:\n");
@@ -577,7 +574,7 @@
final Map<ClassEntity, Set<ClassEntity>> mixinUses = {};
final CommonElements _commonElements;
- final KernelToElementMap _elementMap;
+ final KernelToElementMapForClassHierarchy _elementMap;
ClassHierarchyBuilder(this._commonElements, this._elementMap);
@@ -597,8 +594,9 @@
ClassHierarchyNode _ensureClassHierarchyNode(ClassEntity cls) {
return _classHierarchyNodes.putIfAbsent(cls, () {
- ClassHierarchyNode parentNode;
- ClassEntity superclass = _elementMap.getSuperClass(cls);
+ cls as IndexedClass; // TODO(48820): Try to remove.
+ ClassHierarchyNode? parentNode;
+ ClassEntity? superclass = _elementMap.getSuperClass(cls);
if (superclass != null) {
parentNode = _ensureClassHierarchyNode(superclass);
}
@@ -609,6 +607,7 @@
ClassSet _ensureClassSet(ClassEntity cls) {
return _classSets.putIfAbsent(cls, () {
+ cls as IndexedClass;
ClassHierarchyNode node = _ensureClassHierarchyNode(cls);
ClassSet classSet = ClassSet(node);
@@ -619,7 +618,7 @@
subtypeSet.addSubtype(node);
}
- ClassEntity appliedMixin = _elementMap.getAppliedMixin(cls);
+ ClassEntity? appliedMixin = _elementMap.getAppliedMixin(cls);
while (appliedMixin != null) {
// TODO(johnniwinther): Use the data stored in [ClassSet].
registerMixinUse(cls, appliedMixin);
@@ -633,7 +632,10 @@
// class C = Object with B;
//
// we need to register that C not only mixes in B but also A.
- appliedMixin = _elementMap.getAppliedMixin(appliedMixin);
+
+ // TODO(48820): Can we remove the need for `as IndexedClass`?
+ appliedMixin =
+ _elementMap.getAppliedMixin(appliedMixin as IndexedClass);
}
return classSet;
});
@@ -642,14 +644,14 @@
void _updateSuperClassHierarchyNodeForClass(ClassHierarchyNode node) {
// Ensure that classes implicitly implementing `Function` are in its
// subtype set.
- ClassEntity cls = node.cls;
+ final cls = node.cls;
if (cls != _commonElements.functionClass &&
_elementMap.implementsFunction(cls)) {
ClassSet subtypeSet = _ensureClassSet(_commonElements.functionClass);
subtypeSet.addSubtype(node);
}
if (!node.isInstantiated && node.parentNode != null) {
- _updateSuperClassHierarchyNodeForClass(node.parentNode);
+ _updateSuperClassHierarchyNodeForClass(node.parentNode!);
}
}
@@ -676,12 +678,10 @@
bool _isSubtypeOf(ClassEntity x, ClassEntity y) {
assert(_classSets.containsKey(x),
"ClassSet for $x has not been computed yet.");
- ClassSet classSet = _classSets[y];
- assert(classSet != null,
- failedAt(y, "No ClassSet for $y (${y.runtimeType}): ${_classSets}"));
- ClassHierarchyNode classHierarchyNode = _classHierarchyNodes[x];
- assert(classHierarchyNode != null,
- failedAt(x, "No ClassHierarchyNode for $x"));
+ ClassSet classSet = _classSets[y] ??
+ failedAt(y, "No ClassSet for $y (${y.runtimeType}): ${_classSets}");
+ ClassHierarchyNode classHierarchyNode =
+ _classHierarchyNodes[x] ?? failedAt(x, "No ClassHierarchyNode for $x");
return classSet.hasSubtype(classHierarchyNode);
}
@@ -689,13 +689,13 @@
/// target a member declared in [memberHoldingClass].
bool isInheritedInExactClass(
ClassEntity memberHoldingClass, ClassEntity exactClass) {
- ClassHierarchyNode exactClassNode = _classHierarchyNodes[exactClass];
+ ClassHierarchyNode exactClassNode = _classHierarchyNodes[exactClass]!;
if (!exactClassNode.isAbstractlyInstantiated &&
!exactClassNode.isDirectlyInstantiated) {
// No instances of [thisClass] are live.
return false;
}
- ClassSet memberHoldingClassSet = _classSets[memberHoldingClass];
+ ClassSet memberHoldingClassSet = _classSets[memberHoldingClass]!;
if (memberHoldingClassSet.hasSubclass(exactClassNode)) {
/// A member from a super class can be accessed.
return true;
@@ -737,23 +737,23 @@
/// member holding class, can be inherited into a live class.
class _InheritedInThisClassCache {
/// Set of classes that inherits members from the member holding class.
- Set<ClassEntity> _inheritingClasses;
+ Set<ClassEntity>? _inheritingClasses;
/// Cache for liveness computation for a `this` expressions of a given class.
- Map<ClassEntity, _LiveSet> _map;
+ Map<ClassEntity, _LiveSet>? _map;
/// Returns `true` if members of [memberHoldingClass] can be inherited into
/// a live class that can be the target of a `this` expression in [thisClass].
bool isInheritedInThisClassOf(ClassHierarchyBuilder builder,
ClassEntity memberHoldingClass, ClassEntity thisClass) {
- _LiveSet set;
+ _LiveSet? set;
if (_map == null) {
_map = {};
} else {
- set = _map[thisClass];
+ set = _map![thisClass];
}
if (set == null) {
- set = _map[thisClass] = _computeInheritingInThisClassSet(
+ set = _map![thisClass] = _computeInheritingInThisClassSet(
builder, memberHoldingClass, thisClass);
}
return set.hasLiveClass(builder);
@@ -762,15 +762,15 @@
_LiveSet _computeInheritingInThisClassSet(ClassHierarchyBuilder builder,
ClassEntity memberHoldingClass, ClassEntity thisClass) {
ClassHierarchyNode memberHoldingClassNode =
- builder._classHierarchyNodes[memberHoldingClass];
+ builder._classHierarchyNodes[memberHoldingClass]!;
if (_inheritingClasses == null) {
_inheritingClasses = {};
- _inheritingClasses.addAll(memberHoldingClassNode
+ _inheritingClasses!.addAll(memberHoldingClassNode
.subclassesByMask(ClassHierarchyNode.ALL, strict: false));
for (ClassHierarchyNode mixinApplication
- in builder._classSets[memberHoldingClass].mixinApplicationNodes) {
- _inheritingClasses.addAll(mixinApplication
+ in builder._classSets[memberHoldingClass]!.mixinApplicationNodes) {
+ _inheritingClasses!.addAll(mixinApplication
.subclassesByMask(ClassHierarchyNode.ALL, strict: false));
}
}
@@ -778,9 +778,9 @@
Set<ClassEntity> validatingSet = {};
void processHierarchy(ClassHierarchyNode mixerNode) {
- for (ClassEntity inheritingClass in _inheritingClasses) {
+ for (ClassEntity inheritingClass in _inheritingClasses!) {
ClassHierarchyNode inheritingClassNode =
- builder._classHierarchyNodes[inheritingClass];
+ builder._classHierarchyNodes[inheritingClass]!;
if (!validatingSet.contains(mixerNode.cls) &&
inheritingClassNode.hasSubclass(mixerNode)) {
// If [mixerNode.cls] is live then a `this` expression can target
@@ -796,7 +796,7 @@
}
}
- ClassSet thisClassSet = builder._classSets[thisClass];
+ ClassSet thisClassSet = builder._classSets[thisClass]!;
processHierarchy(thisClassSet.node);
@@ -811,20 +811,20 @@
/// A cache object used for [ClassHierarchyBuilder.isInheritedInSubtypeOf].
class _InheritedInSubtypeCache {
- Map<ClassEntity, _LiveSet> _map;
+ Map<ClassEntity, _LiveSet>? _map;
/// Returns whether a live class currently known to inherit from [x] and
/// implement [y].
bool isInheritedInSubtypeOf(
ClassHierarchyBuilder builder, ClassEntity x, ClassEntity y) {
- _LiveSet set;
+ _LiveSet? set;
if (_map == null) {
_map = {};
} else {
- set = _map[y];
+ set = _map![y];
}
if (set == null) {
- set = _map[y] = _computeInheritingInSubtypeSet(builder, x, y);
+ set = _map![y] = _computeInheritingInSubtypeSet(builder, x, y);
}
return set.hasLiveClass(builder);
}
@@ -833,12 +833,7 @@
/// while implementing class [y].
_LiveSet _computeInheritingInSubtypeSet(
ClassHierarchyBuilder builder, ClassEntity x, ClassEntity y) {
- ClassSet classSet = builder._classSets[x];
-
- assert(
- classSet != null,
- failedAt(
- x, "No ClassSet for $x (${x.runtimeType}): ${builder._classSets}"));
+ ClassSet classSet = builder._classSets[x]!;
Set<ClassEntity> classes = {};
@@ -848,12 +843,12 @@
}
/// Add subclasses of [node] that implement [y].
- void subclassImplements(ClassHierarchyNode node, {bool strict}) {
+ void subclassImplements(ClassHierarchyNode node, {required bool strict}) {
node.forEachSubclass((ClassEntity z) {
if (builder._isSubtypeOf(z, y)) {
classes.add(z);
}
- return null;
+ return IterationStep.CONTINUE;
}, ClassHierarchyNode.ALL, strict: strict);
}
@@ -881,8 +876,8 @@
/// therefore known never to contain live classes. In this case [_classes]
/// is `null`. If `null` [_classes] is a non-empty set containing classes
/// that are not yet known to be live.
- bool _result;
- Set<ClassEntity> _classes;
+ bool? _result;
+ Set<ClassEntity>? _classes;
_LiveSet(Set<ClassEntity> classes)
: _result = classes.isEmpty ? false : null,
@@ -901,9 +896,9 @@
/// `true` (because at least one class is known to be live) we will continue
/// to return `true`.
bool hasLiveClass(ClassHierarchyBuilder builder) {
- if (_result != null) return _result;
- for (ClassEntity cls in _classes) {
- if (builder._classHierarchyNodes[cls].isInstantiated) {
+ if (_result != null) return _result!;
+ for (ClassEntity cls in _classes!) {
+ if (builder._classHierarchyNodes[cls]!.isInstantiated) {
// We now know this set contains a live class and done need to remember
// that set of classes anymore.
_result = true;
@@ -958,11 +953,13 @@
/// Result computed in [ClassHierarchy.commonSubclasses].
class SubclassResult {
final SubclassResultKind kind;
- final List<ClassEntity> classes;
+ final List<ClassEntity>? _classes;
- SubclassResult(this.classes) : kind = SubclassResultKind.SET;
+ List<ClassEntity> get classes => _classes!;
- const SubclassResult.internal(this.kind) : classes = null;
+ SubclassResult(this._classes) : kind = SubclassResultKind.SET;
+
+ const SubclassResult.internal(this.kind) : _classes = null;
static const SubclassResult EMPTY =
SubclassResult.internal(SubclassResultKind.EMPTY);
@@ -980,5 +977,5 @@
SubclassResult.internal(SubclassResultKind.SUBTYPE2);
@override
- String toString() => 'SubclassResult($kind,classes=$classes)';
+ String toString() => 'SubclassResult($kind,classes=$_classes)';
}
diff --git a/pkg/dart2wasm/lib/code_generator.dart b/pkg/dart2wasm/lib/code_generator.dart
index 8671f20..113b1bc 100644
--- a/pkg/dart2wasm/lib/code_generator.dart
+++ b/pkg/dart2wasm/lib/code_generator.dart
@@ -1548,6 +1548,7 @@
b.i64_const(2011);
break;
case "runtimeType":
+ case "_runtimeType":
wrap(ConstantExpression(TypeLiteralConstant(NullType())), resultType);
break;
default:
@@ -1903,7 +1904,7 @@
@override
w.ValueType visitStringConcatenation(
StringConcatenation node, w.ValueType expectedType) {
- makeList(node.expressions, translator.fixedLengthListClass,
+ makeListFromExpressions(node.expressions,
InterfaceType(translator.stringBaseClass, Nullability.nonNullable));
return call(translator.stringInterpolate.reference);
}
@@ -1972,18 +1973,24 @@
@override
w.ValueType visitListLiteral(ListLiteral node, w.ValueType expectedType) {
- return makeList(
- node.expressions, translator.growableListClass, node.typeArgument);
+ return makeListFromExpressions(node.expressions, node.typeArgument,
+ isGrowable: true);
}
- w.ValueType makeList(
- List<Expression> expressions, Class cls, DartType typeArg) {
+ /// Takes a List class, a type argument, a function which will be called for
+ /// each item in the list with the expected type of the element, and a list
+ /// length, and creates a Dart List on the stack.
+ w.ValueType makeList(DartType typeArg, int length,
+ void Function(w.ValueType, int) generateItem,
+ {bool isGrowable = false}) {
+ Class cls = isGrowable
+ ? translator.growableListClass
+ : translator.fixedLengthListClass;
ClassInfo info = translator.classInfo[cls]!;
translator.functions.allocateClass(info.classId);
w.RefType refType = info.struct.fields.last.type.unpacked as w.RefType;
w.ArrayType arrayType = refType.heapType as w.ArrayType;
w.ValueType elementType = arrayType.elementType.type.unpacked;
- int length = expressions.length;
b.i32_const(info.classId);
b.i32_const(initialIdentityHash);
@@ -1999,7 +2006,7 @@
for (int i = 0; i < length; i++) {
b.local_get(arrayLocal);
b.i32_const(i);
- wrap(expressions[i], elementType);
+ generateItem(elementType, i);
b.array_set(arrayType);
}
b.local_get(arrayLocal);
@@ -2008,8 +2015,8 @@
}
}
} else {
- for (Expression expression in expressions) {
- wrap(expression, elementType);
+ for (int i = 0; i < length; i++) {
+ generateItem(elementType, i);
}
translator.array_init(b, arrayType, length);
}
@@ -2018,6 +2025,13 @@
return info.nonNullableType;
}
+ w.ValueType makeListFromExpressions(
+ List<Expression> expressions, DartType typeArg,
+ {bool isGrowable = false}) =>
+ makeList(typeArg, expressions.length,
+ (w.ValueType elementType, int i) => wrap(expressions[i], elementType),
+ isGrowable: isGrowable);
+
@override
w.ValueType visitMapLiteral(MapLiteral node, w.ValueType expectedType) {
w.BaseFunction mapFactory =
diff --git a/pkg/dart2wasm/lib/intrinsics.dart b/pkg/dart2wasm/lib/intrinsics.dart
index e59f140..e4d3da9 100644
--- a/pkg/dart2wasm/lib/intrinsics.dart
+++ b/pkg/dart2wasm/lib/intrinsics.dart
@@ -581,6 +581,14 @@
return null;
}
+ w.ValueType getID(Expression node) {
+ ClassInfo info = translator.topInfo;
+ codeGen.wrap(node, info.nullableType);
+ b.struct_get(info.struct, FieldIndex.classId);
+ b.i64_extend_i32_u();
+ return w.NumType.i64;
+ }
+
w.ValueType? generateStaticIntrinsic(StaticInvocation node) {
String name = node.name.text;
Class? cls = node.target.enclosingClass;
@@ -643,6 +651,18 @@
return translator.types.makeTypeRulesSupers(b);
case "_getTypeRulesSubstitutions":
return translator.types.makeTypeRulesSubstitutions(b);
+ case "_getInterfaceTypeRuntimeType":
+ Expression object = node.arguments.positional[0];
+ Expression typeArguments = node.arguments.positional[1];
+ ClassInfo info = translator.classInfo[translator.interfaceTypeClass]!;
+ b.i32_const(info.classId);
+ b.i32_const(initialIdentityHash);
+ // Runtime types are never nullable.
+ b.i32_const(0);
+ getID(object);
+ codeGen.wrap(typeArguments, translator.types.typeListExpectedType);
+ translator.struct_new(b, info);
+ return info.nonNullableType;
}
}
@@ -741,12 +761,7 @@
b.f64_reinterpret_i64();
return w.NumType.f64;
case "getID":
- assert(cls?.name == "ClassID");
- ClassInfo info = translator.topInfo;
- codeGen.wrap(node.arguments.positional.single, info.nullableType);
- b.struct_get(info.struct, FieldIndex.classId);
- b.i64_extend_i32_u();
- return w.NumType.i64;
+ return getID(node.arguments.positional.single);
}
}
@@ -975,29 +990,15 @@
}
// Object.runtimeType
- // TODO(joshualitt): Implement this correctly for [FunctionType] and
- // [InterfaceType].
if (member.enclosingClass == translator.coreTypes.objectClass &&
name == "runtimeType") {
+ // Simple redirect to `_runtimeType`. This is done to keep
+ // `Object.runtimeType` external, which seems to be necessary for the TFA.
+ // If we don't do this, then the TFA assumes things like
+ // `null.runtimeType` are impossible and inserts a throw.
w.Local receiver = paramLocals[0];
- ClassInfo info = translator.classInfo[translator.interfaceTypeClass]!;
- translator.functions.allocateClass(info.classId);
- w.ValueType typeListExpectedType = info
- .struct.fields[FieldIndex.interfaceTypeTypeArguments].type.unpacked;
-
- b.i32_const(info.classId);
- b.i32_const(initialIdentityHash);
- // Runtime types are never nullable.
- b.i32_const(0);
b.local_get(receiver);
- b.struct_get(translator.topInfo.struct, FieldIndex.classId);
- b.i64_extend_i32_u();
- // TODO(askesc): Type arguments
- b.global_get(translator.constants.emptyTypeList);
- translator.convertType(function,
- translator.constants.emptyTypeList.type.type, typeListExpectedType);
- translator.struct_new(b, info);
-
+ codeGen.call(translator.objectRuntimeType.reference);
return true;
}
@@ -1082,6 +1083,22 @@
return true;
}
+ // _typeArguments
+ if (member.name.text == "_typeArguments") {
+ Class cls = member.enclosingClass!;
+ ClassInfo classInfo = translator.classInfo[cls]!;
+ w.Local object = paramLocals[0];
+ codeGen.makeList(translator.types.typeType, cls.typeParameters.length,
+ (w.ValueType elementType, int i) {
+ TypeParameter typeParameter = cls.typeParameters[i];
+ int typeParameterIndex = translator.typeParameterIndex[typeParameter]!;
+ b.local_get(object);
+ translator.ref_cast(b, classInfo);
+ b.struct_get(classInfo.struct, typeParameterIndex);
+ });
+ return true;
+ }
+
// (Int|Uint|Float)(8|16|32|64)(Clamped)?(List|ArrayView) constructors
if (member.isExternal &&
member.enclosingLibrary.name == "dart.typed_data") {
diff --git a/pkg/dart2wasm/lib/transformers.dart b/pkg/dart2wasm/lib/transformers.dart
index cb5a52f..3351fa7 100644
--- a/pkg/dart2wasm/lib/transformers.dart
+++ b/pkg/dart2wasm/lib/transformers.dart
@@ -24,12 +24,20 @@
Member? _currentMember;
StaticTypeContext? _cachedTypeContext;
+ final Library _coreLibrary;
+ final InterfaceType _nonNullableTypeType;
StaticTypeContext get typeContext =>
_cachedTypeContext ??= StaticTypeContext(_currentMember!, env);
+ CoreTypes get coreTypes => env.coreTypes;
+
_WasmTransformer(CoreTypes coreTypes, ClassHierarchy hierarchy)
- : env = TypeEnvironment(coreTypes, hierarchy);
+ : env = TypeEnvironment(coreTypes, hierarchy),
+ _nonNullableTypeType = coreTypes.index
+ .getClass('dart:core', '_Type')
+ .getThisType(coreTypes, Nullability.nonNullable),
+ _coreLibrary = coreTypes.index.getLibrary('dart:core');
@override
defaultMember(Member node) {
@@ -43,6 +51,50 @@
return result;
}
+ /// We can reuse a superclass' `_typeArguments` method if the subclass and the
+ /// superclass have the exact same type parameters in the exact same order.
+ bool canReuseSuperMethod(Class cls) {
+ Supertype supertype = cls.supertype!;
+ if (cls.typeParameters.length != supertype.typeArguments.length) {
+ return false;
+ }
+ for (int i = 0; i < cls.typeParameters.length; i++) {
+ TypeParameter parameter = cls.typeParameters[i];
+ DartType arg = supertype.typeArguments[i];
+ if (arg is! TypeParameterType || arg.parameter != parameter) {
+ return false;
+ }
+ }
+ return true;
+ }
+
+ @override
+ TreeNode visitClass(Class cls) {
+ // For every concrete class whose type parameters do not match the type
+ // parameters of it's super class we embed a special virtual function
+ // `_getTypeArguments`. When generating code for `_getTypeArguments`, we
+ // read the `TypeParameter`s off the instantiated object and generate a
+ // `List<Type>` to pass to `_getRuntimeType` which then returns a reified
+ // `Type` object.
+ if (!cls.isAbstract &&
+ cls != coreTypes.objectClass &&
+ !canReuseSuperMethod(cls)) {
+ Procedure getTypeArguments = Procedure(
+ Name("_typeArguments", _coreLibrary),
+ ProcedureKind.Getter,
+ FunctionNode(
+ null,
+ returnType: InterfaceType(coreTypes.listClass,
+ Nullability.nonNullable, [_nonNullableTypeType]),
+ ),
+ isExternal: true,
+ fileUri: cls.fileUri)
+ ..isNonNullableByDefault = true;
+ cls.addProcedure(getTypeArguments);
+ }
+ return super.visitClass(cls);
+ }
+
@override
TreeNode visitForInStatement(ForInStatement stmt) {
// Transform
diff --git a/pkg/dart2wasm/lib/translator.dart b/pkg/dart2wasm/lib/translator.dart
index ce2a835..50e7b0a 100644
--- a/pkg/dart2wasm/lib/translator.dart
+++ b/pkg/dart2wasm/lib/translator.dart
@@ -122,6 +122,7 @@
late final Procedure setAdd;
late final Procedure hashImmutableIndexNullable;
late final Procedure isSubtype;
+ late final Procedure objectRuntimeType;
late final Map<Class, w.StorageType> builtinTypes;
late final Map<w.ValueType, Class> boxedClasses;
@@ -260,6 +261,9 @@
.firstWhere((l) => l.name == "dart.core")
.procedures
.firstWhere((p) => p.name.text == "_isSubtype");
+ objectRuntimeType = lookupCore("Object")
+ .procedures
+ .firstWhere((p) => p.name.text == "_runtimeType");
builtinTypes = {
coreTypes.boolClass: w.NumType.i32,
coreTypes.intClass: w.NumType.i64,
diff --git a/pkg/dart2wasm/lib/types.dart b/pkg/dart2wasm/lib/types.dart
index 371f1c9..50e4283 100644
--- a/pkg/dart2wasm/lib/types.dart
+++ b/pkg/dart2wasm/lib/types.dart
@@ -78,6 +78,9 @@
InterfaceType get namedParameterType =>
InterfaceType(translator.namedParameterClass, Nullability.nonNullable);
+ InterfaceType get typeType =>
+ InterfaceType(translator.typeClass, Nullability.nonNullable);
+
CoreTypes get coreTypes => translator.coreTypes;
/// Builds a [Map<int, Map<int, List<DartType>>>] to store subtype
@@ -257,10 +260,8 @@
}
void _makeTypeList(CodeGenerator codeGen, List<DartType> types) {
- w.ValueType listType = codeGen.makeList(
- types.map((t) => TypeLiteral(t)).toList(),
- translator.fixedLengthListClass,
- InterfaceType(translator.typeClass, Nullability.nonNullable));
+ w.ValueType listType = codeGen.makeListFromExpressions(
+ types.map((t) => TypeLiteral(t)).toList(), typeType);
translator.convertType(codeGen.function, listType, typeListExpectedType);
}
@@ -333,8 +334,8 @@
BoolLiteral(n.isRequired)
])));
}
- w.ValueType namedParametersListType = codeGen.makeList(
- expressions, translator.fixedLengthListClass, namedParameterType);
+ w.ValueType namedParametersListType =
+ codeGen.makeListFromExpressions(expressions, namedParameterType);
translator.convertType(codeGen.function, namedParametersListType,
namedParametersExpectedType);
}
diff --git a/runtime/vm/heap/heap.cc b/runtime/vm/heap/heap.cc
index 2b021a0..d8b0c3f 100644
--- a/runtime/vm/heap/heap.cc
+++ b/runtime/vm/heap/heap.cc
@@ -485,9 +485,11 @@
}
{
GcSafepointOperationScope safepoint_operation(thread);
- if (reason == GCReason::kFinalize &&
- old_space_.phase() != PageSpace::kAwaitingFinalization) {
- return; // Lost race.
+ if (reason == GCReason::kFinalize) {
+ MonitorLocker ml(old_space_.tasks_lock());
+ if (old_space_.phase() != PageSpace::kAwaitingFinalization) {
+ return; // Lost race.
+ }
}
thread->isolate_group()->ForEachIsolate(
diff --git a/sdk/lib/_internal/wasm/lib/object_patch.dart b/sdk/lib/_internal/wasm/lib/object_patch.dart
index d38ca14..8b727d2 100644
--- a/sdk/lib/_internal/wasm/lib/object_patch.dart
+++ b/sdk/lib/_internal/wasm/lib/object_patch.dart
@@ -8,6 +8,9 @@
external int _getHash(Object obj);
external void _setHash(Object obj, int hash);
+external _Type _getInterfaceTypeRuntimeType(
+ Object object, List<Type> typeArguments);
+
@patch
class Object {
@patch
@@ -34,6 +37,16 @@
int get hashCode => _objectHashCode(this);
int get _identityHashCode => _objectHashCode(this);
+ /// Concrete subclasses of [Object] will have overrides of [_typeArguments]
+ /// which return their type arguments.
+ List<Type> get _typeArguments => const [];
+
+ /// We use [_runtimeType] for internal type testing, because objects can
+ /// override [runtimeType].
+ @patch
+ external Type get runtimeType;
+ _Type get _runtimeType => _getInterfaceTypeRuntimeType(this, _typeArguments);
+
@patch
String toString() => _toString(this);
// A statically dispatched version of Object.toString.
@@ -43,7 +56,4 @@
dynamic noSuchMethod(Invocation invocation) {
throw new NoSuchMethodError.withInvocation(this, invocation);
}
-
- @patch
- external Type get runtimeType;
}
diff --git a/sdk/lib/_internal/wasm/lib/type.dart b/sdk/lib/_internal/wasm/lib/type.dart
index fcee927..4a1ea76 100644
--- a/sdk/lib/_internal/wasm/lib/type.dart
+++ b/sdk/lib/_internal/wasm/lib/type.dart
@@ -669,6 +669,5 @@
@pragma("wasm:entry-point")
bool _isSubtype(Object? s, _Type t) {
- return _typeUniverse.isSubtype(
- unsafeCast<_Type>(s.runtimeType), null, t, null);
+ return _typeUniverse.isSubtype(s._runtimeType, null, t, null);
}
diff --git a/tests/standalone/io/http_auth_digest_test.dart b/tests/standalone/io/http_auth_digest_test.dart
index 11e3ecf..5a533a2 100644
--- a/tests/standalone/io/http_auth_digest_test.dart
+++ b/tests/standalone/io/http_auth_digest_test.dart
@@ -2,12 +2,12 @@
// 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:async';
+import 'dart:io';
+
import "package:convert/convert.dart";
import "package:crypto/crypto.dart";
import "package:expect/expect.dart";
-import 'dart:async';
-import 'dart:io';
-import 'dart:isolate';
class Server {
late HttpServer server;
diff --git a/tests/standalone/io/http_auth_test.dart b/tests/standalone/io/http_auth_test.dart
index 9b01075..4c0a165 100644
--- a/tests/standalone/io/http_auth_test.dart
+++ b/tests/standalone/io/http_auth_test.dart
@@ -2,12 +2,11 @@
// 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 "package:crypto/crypto.dart";
-import "package:expect/expect.dart";
import 'dart:async';
-import 'dart:io';
-import 'dart:isolate';
import 'dart:convert';
+import 'dart:io';
+
+import "package:expect/expect.dart";
class Server {
late HttpServer server;
diff --git a/tests/standalone/io/http_proxy_advanced_test.dart b/tests/standalone/io/http_proxy_advanced_test.dart
index 65e4db9..d29a42d 100644
--- a/tests/standalone/io/http_proxy_advanced_test.dart
+++ b/tests/standalone/io/http_proxy_advanced_test.dart
@@ -7,12 +7,12 @@
// OtherResources=certificates/trusted_certs.pem
import "dart:async";
-import "dart:io";
import 'dart:convert';
+import "dart:io";
+
import "package:convert/convert.dart";
import "package:crypto/crypto.dart";
import "package:expect/expect.dart";
-import "package:path/path.dart";
String localFile(path) => Platform.script.resolve(path).toFilePath();
diff --git a/tests/standalone/io/http_proxy_test.dart b/tests/standalone/io/http_proxy_test.dart
index 58ecb8e..d13d0ba 100644
--- a/tests/standalone/io/http_proxy_test.dart
+++ b/tests/standalone/io/http_proxy_test.dart
@@ -7,8 +7,9 @@
// OtherResources=certificates/trusted_certs.pem
import "dart:async";
-import "dart:io";
import 'dart:convert';
+import "dart:io";
+
import "package:convert/convert.dart";
import "package:crypto/crypto.dart";
import "package:expect/expect.dart";
diff --git a/tests/standalone/io/web_socket_compression_test.dart b/tests/standalone/io/web_socket_compression_test.dart
index 56ada33..01e7269 100644
--- a/tests/standalone/io/web_socket_compression_test.dart
+++ b/tests/standalone/io/web_socket_compression_test.dart
@@ -10,13 +10,12 @@
import "dart:async";
import "dart:convert";
import "dart:io";
-import "dart:typed_data";
import "dart:math";
+import "dart:typed_data";
import "package:async_helper/async_helper.dart";
import "package:crypto/crypto.dart";
import "package:expect/expect.dart";
-import "package:path/path.dart";
const WEB_SOCKET_GUID = "258EAFA5-E914-47DA-95CA-C5AB0DC85B11";
diff --git a/tests/standalone_2/io/http_auth_digest_test.dart b/tests/standalone_2/io/http_auth_digest_test.dart
index 42d34ae..6ac5056 100644
--- a/tests/standalone_2/io/http_auth_digest_test.dart
+++ b/tests/standalone_2/io/http_auth_digest_test.dart
@@ -4,12 +4,12 @@
// @dart = 2.9
+import 'dart:async';
+import 'dart:io';
+
import "package:convert/convert.dart";
import "package:crypto/crypto.dart";
import "package:expect/expect.dart";
-import 'dart:async';
-import 'dart:io';
-import 'dart:isolate';
class Server {
HttpServer server;
diff --git a/tests/standalone_2/io/http_auth_test.dart b/tests/standalone_2/io/http_auth_test.dart
index 231b182..669523c 100644
--- a/tests/standalone_2/io/http_auth_test.dart
+++ b/tests/standalone_2/io/http_auth_test.dart
@@ -4,12 +4,11 @@
// @dart = 2.9
-import "package:crypto/crypto.dart";
-import "package:expect/expect.dart";
import 'dart:async';
-import 'dart:io';
-import 'dart:isolate';
import 'dart:convert';
+import 'dart:io';
+
+import "package:expect/expect.dart";
class Server {
HttpServer server;
diff --git a/tests/standalone_2/io/http_proxy_advanced_test.dart b/tests/standalone_2/io/http_proxy_advanced_test.dart
index a25f774..38dd62b 100644
--- a/tests/standalone_2/io/http_proxy_advanced_test.dart
+++ b/tests/standalone_2/io/http_proxy_advanced_test.dart
@@ -9,12 +9,12 @@
// OtherResources=certificates/trusted_certs.pem
import "dart:async";
-import "dart:io";
import 'dart:convert';
+import "dart:io";
+
import "package:convert/convert.dart";
import "package:crypto/crypto.dart";
import "package:expect/expect.dart";
-import "package:path/path.dart";
String localFile(path) => Platform.script.resolve(path).toFilePath();
diff --git a/tests/standalone_2/io/http_proxy_test.dart b/tests/standalone_2/io/http_proxy_test.dart
index c3ec4e9..ffba7c9 100644
--- a/tests/standalone_2/io/http_proxy_test.dart
+++ b/tests/standalone_2/io/http_proxy_test.dart
@@ -9,8 +9,9 @@
// OtherResources=certificates/trusted_certs.pem
import "dart:async";
-import "dart:io";
import 'dart:convert';
+import "dart:io";
+
import "package:convert/convert.dart";
import "package:crypto/crypto.dart";
import "package:expect/expect.dart";
diff --git a/tests/standalone_2/io/web_socket_compression_test.dart b/tests/standalone_2/io/web_socket_compression_test.dart
index c62a521..b420463 100644
--- a/tests/standalone_2/io/web_socket_compression_test.dart
+++ b/tests/standalone_2/io/web_socket_compression_test.dart
@@ -12,13 +12,12 @@
import "dart:async";
import "dart:convert";
import "dart:io";
-import "dart:typed_data";
import "dart:math";
+import "dart:typed_data";
import "package:async_helper/async_helper.dart";
import "package:crypto/crypto.dart";
import "package:expect/expect.dart";
-import "package:path/path.dart";
const WEB_SOCKET_GUID = "258EAFA5-E914-47DA-95CA-C5AB0DC85B11";
diff --git a/tools/VERSION b/tools/VERSION
index 234f0fe..dae6e49 100644
--- a/tools/VERSION
+++ b/tools/VERSION
@@ -27,5 +27,5 @@
MAJOR 2
MINOR 18
PATCH 0
-PRERELEASE 227
+PRERELEASE 228
PRERELEASE_PATCH 0
\ No newline at end of file