Version 2.16.0-85.0.dev

Merge commit '0d98f6ab5d56505033f0b3b29c8bb46f85461011' into 'dev'
diff --git a/pkg/analysis_server/lib/src/services/completion/dart/arglist_contributor.dart b/pkg/analysis_server/lib/src/services/completion/dart/arglist_contributor.dart
index a6ff620..21f5f37 100644
--- a/pkg/analysis_server/lib/src/services/completion/dart/arglist_contributor.dart
+++ b/pkg/analysis_server/lib/src/services/completion/dart/arglist_contributor.dart
@@ -7,6 +7,7 @@
 import 'package:analysis_server/src/services/completion/dart/completion_manager.dart';
 import 'package:analysis_server/src/services/completion/dart/suggestion_builder.dart';
 import 'package:analysis_server/src/utilities/flutter.dart';
+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';
@@ -100,7 +101,9 @@
     if (_isEditingNamedArgLabel() ||
         _isAppendingToArgList() ||
         _isAddingLabelToPositional()) {
-      if (requiredCount == 0 || requiredCount < _argCount()) {
+      if (request.featureSet.isEnabled(Feature.named_arguments_anywhere) ||
+          requiredCount == 0 ||
+          requiredCount < _argCount()) {
         // If there's a replacement range that starts at the caret, it will be
         // for an identifier that is not the named label and therefore it should
         // not be replaced.
diff --git a/pkg/analysis_server/lib/src/services/correction/assist_internal.dart b/pkg/analysis_server/lib/src/services/correction/assist_internal.dart
index c2e4e39..2e8d400 100644
--- a/pkg/analysis_server/lib/src/services/correction/assist_internal.dart
+++ b/pkg/analysis_server/lib/src/services/correction/assist_internal.dart
@@ -221,7 +221,7 @@
     for (var multiGenerator in multiGenerators) {
       var multiProducer = multiGenerator();
       multiProducer.configure(context);
-      for (var producer in multiProducer.producers) {
+      await for (var producer in multiProducer.producers) {
         await compute(producer);
       }
     }
diff --git a/pkg/analysis_server/lib/src/services/correction/bulk_fix_processor.dart b/pkg/analysis_server/lib/src/services/correction/bulk_fix_processor.dart
index 0b6145c..4303a94 100644
--- a/pkg/analysis_server/lib/src/services/correction/bulk_fix_processor.dart
+++ b/pkg/analysis_server/lib/src/services/correction/bulk_fix_processor.dart
@@ -383,7 +383,7 @@
           for (var multiGenerator in multiGenerators) {
             var multiProducer = multiGenerator();
             multiProducer.configure(context);
-            for (var producer in multiProducer.producers) {
+            await for (var producer in multiProducer.producers) {
               await _generateFix(context, producer, codeName);
             }
           }
diff --git a/pkg/analysis_server/lib/src/services/correction/dart/abstract_producer.dart b/pkg/analysis_server/lib/src/services/correction/dart/abstract_producer.dart
index 56442ae..03e3a19 100644
--- a/pkg/analysis_server/lib/src/services/correction/dart/abstract_producer.dart
+++ b/pkg/analysis_server/lib/src/services/correction/dart/abstract_producer.dart
@@ -302,7 +302,7 @@
 /// assists).
 abstract class MultiCorrectionProducer extends _AbstractCorrectionProducer {
   /// Return each of the individual producers generated by this producer.
-  Iterable<CorrectionProducer> get producers;
+  Stream<CorrectionProducer> get producers;
 }
 
 /// An object that can compute a correction (fix or assist) in a Dart file.
diff --git a/pkg/analysis_server/lib/src/services/correction/dart/add_missing_parameter.dart b/pkg/analysis_server/lib/src/services/correction/dart/add_missing_parameter.dart
index 1f11731..04adf5d 100644
--- a/pkg/analysis_server/lib/src/services/correction/dart/add_missing_parameter.dart
+++ b/pkg/analysis_server/lib/src/services/correction/dart/add_missing_parameter.dart
@@ -11,7 +11,7 @@
 
 class AddMissingParameter extends MultiCorrectionProducer {
   @override
-  Iterable<CorrectionProducer> get producers sync* {
+  Stream<CorrectionProducer> get producers async* {
     // node is the unmatched argument.
     var argumentList = node.parent;
     if (argumentList is! ArgumentList) {
diff --git a/pkg/analysis_server/lib/src/services/correction/dart/add_super_constructor_invocation.dart b/pkg/analysis_server/lib/src/services/correction/dart/add_super_constructor_invocation.dart
index fa1537b..86f5968 100644
--- a/pkg/analysis_server/lib/src/services/correction/dart/add_super_constructor_invocation.dart
+++ b/pkg/analysis_server/lib/src/services/correction/dart/add_super_constructor_invocation.dart
@@ -13,7 +13,7 @@
 
 class AddSuperConstructorInvocation extends MultiCorrectionProducer {
   @override
-  Iterable<CorrectionProducer> get producers sync* {
+  Stream<CorrectionProducer> get producers async* {
     var targetConstructor = node.parent;
     if (targetConstructor is! ConstructorDeclaration) {
       return;
diff --git a/pkg/analysis_server/lib/src/services/correction/dart/change_argument_name.dart b/pkg/analysis_server/lib/src/services/correction/dart/change_argument_name.dart
index 0442afb..54c57a4 100644
--- a/pkg/analysis_server/lib/src/services/correction/dart/change_argument_name.dart
+++ b/pkg/analysis_server/lib/src/services/correction/dart/change_argument_name.dart
@@ -17,7 +17,7 @@
   static const _maxDistance = 4;
 
   @override
-  Iterable<CorrectionProducer> get producers sync* {
+  Stream<CorrectionProducer> get producers async* {
     var namedContext = _getNamedParameterNames();
     if (namedContext == null) {
       return;
diff --git a/pkg/analysis_server/lib/src/services/correction/dart/create_constructor_super.dart b/pkg/analysis_server/lib/src/services/correction/dart/create_constructor_super.dart
index a40ed18..98ac8d5 100644
--- a/pkg/analysis_server/lib/src/services/correction/dart/create_constructor_super.dart
+++ b/pkg/analysis_server/lib/src/services/correction/dart/create_constructor_super.dart
@@ -12,7 +12,7 @@
 
 class CreateConstructorSuper extends MultiCorrectionProducer {
   @override
-  Iterable<CorrectionProducer> get producers sync* {
+  Stream<CorrectionProducer> get producers async* {
     var targetClassNode = node.thisOrAncestorOfType<ClassDeclaration>();
     if (targetClassNode == null) {
       return;
diff --git a/pkg/analysis_server/lib/src/services/correction/dart/data_driven.dart b/pkg/analysis_server/lib/src/services/correction/dart/data_driven.dart
index 9dbbac9..029d157 100644
--- a/pkg/analysis_server/lib/src/services/correction/dart/data_driven.dart
+++ b/pkg/analysis_server/lib/src/services/correction/dart/data_driven.dart
@@ -21,7 +21,7 @@
   static List<TransformSet>? transformSetsForTests;
 
   @override
-  Iterable<CorrectionProducer> get producers sync* {
+  Stream<CorrectionProducer> get producers async* {
     var importedUris = <Uri>[];
     var library = resolvedResult.libraryElement;
     for (var importElement in library.imports) {
diff --git a/pkg/analysis_server/lib/src/services/correction/dart/flutter_wrap.dart b/pkg/analysis_server/lib/src/services/correction/dart/flutter_wrap.dart
index 318a934..94a7a71 100644
--- a/pkg/analysis_server/lib/src/services/correction/dart/flutter_wrap.dart
+++ b/pkg/analysis_server/lib/src/services/correction/dart/flutter_wrap.dart
@@ -15,7 +15,7 @@
 
 class FlutterWrap extends MultiCorrectionProducer {
   @override
-  Iterable<CorrectionProducer> get producers sync* {
+  Stream<CorrectionProducer> get producers async* {
     var widgetExpr = flutter.identifyWidgetExpression(node);
     if (widgetExpr != null) {
       var widgetType = widgetExpr.typeOrThrow;
@@ -36,7 +36,7 @@
     yield* _wrapMultipleWidgets();
   }
 
-  Iterable<CorrectionProducer> _wrapMultipleWidgets() sync* {
+  Stream<CorrectionProducer> _wrapMultipleWidgets() async* {
     var selectionRange = SourceRange(selectionOffset, selectionLength);
     var analyzer = SelectionAnalyzer(selectionRange);
     resolvedResult.unit.accept(analyzer);
diff --git a/pkg/analysis_server/lib/src/services/correction/dart/import_library.dart b/pkg/analysis_server/lib/src/services/correction/dart/import_library.dart
index 4a949c4..4b1ea14 100644
--- a/pkg/analysis_server/lib/src/services/correction/dart/import_library.dart
+++ b/pkg/analysis_server/lib/src/services/correction/dart/import_library.dart
@@ -27,7 +27,7 @@
   ImportLibrary(this._importKind);
 
   @override
-  Iterable<CorrectionProducer> get producers sync* {
+  Stream<CorrectionProducer> get producers async* {
     final node = this.node;
     if (_importKind == _ImportKind.dartAsync) {
       yield* _importLibrary(DartFixKind.IMPORT_ASYNC, Uri.parse('dart:async'));
@@ -42,8 +42,8 @@
     } else if (_importKind == _ImportKind.forExtensionMember) {
       /// Return producers that will import extensions that apply to the
       /// [targetType] and that define a member with the given [memberName].
-      Iterable<CorrectionProducer> importMatchingExtensions(
-          String memberName, DartType? targetType) sync* {
+      Stream<CorrectionProducer> importMatchingExtensions(
+          String memberName, DartType? targetType) async* {
         if (targetType == null) {
           return;
         }
@@ -151,8 +151,8 @@
     return false;
   }
 
-  Iterable<CorrectionProducer> _importExtensionInLibrary(
-      Uri uri, DartType targetType, String memberName) sync* {
+  Stream<CorrectionProducer> _importExtensionInLibrary(
+      Uri uri, DartType targetType, String memberName) async* {
     // Look to see whether the library at the [uri] is already imported. If it
     // is, then we can check the extension elements without needing to perform
     // additional analysis.
@@ -197,31 +197,33 @@
   /// path and a correction with a relative path are returned. If the
   /// `prefer_relative_imports` lint rule is enabled, the relative path is
   /// returned first.
-  Iterable<CorrectionProducer> _importLibrary(
+  Stream<CorrectionProducer> _importLibrary(
     FixKind fixKind,
     Uri library, {
     bool includeRelativeFix = false,
   }) {
     if (!includeRelativeFix) {
-      return [_ImportAbsoluteLibrary(fixKind, library)];
+      return Stream.fromIterable([
+        _ImportAbsoluteLibrary(fixKind, library),
+      ]);
     }
     if (isLintEnabled(LintNames.prefer_relative_imports)) {
-      return [
+      return Stream.fromIterable([
         _ImportRelativeLibrary(fixKind, library),
         _ImportAbsoluteLibrary(fixKind, library),
-      ];
+      ]);
     } else {
-      return [
+      return Stream.fromIterable([
         _ImportAbsoluteLibrary(fixKind, library),
         _ImportRelativeLibrary(fixKind, library),
-      ];
+      ]);
     }
   }
 
-  Iterable<CorrectionProducer> _importLibraryForElement(
+  Stream<CorrectionProducer> _importLibraryForElement(
       String name,
       List<ElementKind> elementKinds,
-      List<TopLevelDeclarationKind> kinds2) sync* {
+      List<TopLevelDeclarationKind> kinds2) async* {
     // ignore if private
     if (name.startsWith('_')) {
       return;
diff --git a/pkg/analysis_server/lib/src/services/correction/dart/surround_with.dart b/pkg/analysis_server/lib/src/services/correction/dart/surround_with.dart
index 84d8648..87abf94 100644
--- a/pkg/analysis_server/lib/src/services/correction/dart/surround_with.dart
+++ b/pkg/analysis_server/lib/src/services/correction/dart/surround_with.dart
@@ -12,7 +12,7 @@
 
 class SurroundWith extends MultiCorrectionProducer {
   @override
-  Iterable<CorrectionProducer> get producers sync* {
+  Stream<CorrectionProducer> get producers async* {
     // If the node is the CompilationUnit, the selected statements must span multiple
     // top level items and cannot be surrounded with anything.
     if (node is CompilationUnit) {
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 26bcfbd..c6fa293 100644
--- a/pkg/analysis_server/lib/src/services/correction/fix_internal.dart
+++ b/pkg/analysis_server/lib/src/services/correction/fix_internal.dart
@@ -1359,7 +1359,7 @@
         for (var multiGenerator in multiGenerators) {
           var multiProducer = multiGenerator();
           multiProducer.configure(context);
-          for (var producer in multiProducer.producers) {
+          await for (var producer in multiProducer.producers) {
             await compute(producer);
           }
         }
diff --git a/pkg/analysis_server/lib/src/utilities/flutter.dart b/pkg/analysis_server/lib/src/utilities/flutter.dart
index b733540..4cb6d42 100644
--- a/pkg/analysis_server/lib/src/utilities/flutter.dart
+++ b/pkg/analysis_server/lib/src/utilities/flutter.dart
@@ -72,64 +72,20 @@
     return null;
   }
 
-  void convertChildToChildren(
-      InstanceCreationExpression childArg,
-      NamedExpression namedExp,
-      String eol,
-      Function getNodeText,
-      Function getLinePrefix,
-      Function getIndent,
-      Function getText,
-      Function _addInsertEdit,
-      Function _addRemoveEdit,
-      Function _addReplaceEdit,
-      Function rangeNode) {
-    var childLoc = namedExp.offset + 'child'.length;
-    _addInsertEdit(childLoc, 'ren');
-    var listLoc = childArg.offset;
-    String childArgSrc = getNodeText(childArg);
-    if (!childArgSrc.contains(eol)) {
-      _addInsertEdit(listLoc, '[');
-      _addInsertEdit(listLoc + childArg.length, ']');
-    } else {
-      var newlineLoc = childArgSrc.lastIndexOf(eol);
-      if (newlineLoc == childArgSrc.length) {
-        newlineLoc -= 1;
-      }
-      String indentOld =
-          getLinePrefix(childArg.offset + eol.length + newlineLoc);
-      var indentNew = '$indentOld${getIndent(1)}';
-      // The separator includes 'child:' but that has no newlines.
-      String separator =
-          getText(namedExp.offset, childArg.offset - namedExp.offset);
-      var prefix = separator.contains(eol) ? '' : '$eol$indentNew';
-      if (prefix.isEmpty) {
-        _addInsertEdit(namedExp.offset + 'child:'.length, ' [');
-        _addRemoveEdit(SourceRange(childArg.offset - 2, 2));
-      } else {
-        _addInsertEdit(listLoc, '[');
-      }
-      var newChildArgSrc = childArgSrc.replaceAll(
-          RegExp('^$indentOld', multiLine: true), '$indentNew');
-      newChildArgSrc = '$prefix$newChildArgSrc,$eol$indentOld]';
-      _addReplaceEdit(rangeNode(childArg), newChildArgSrc);
-    }
-  }
-
   void convertChildToChildren2(
       DartFileEditBuilder builder,
       Expression childArg,
       NamedExpression namedExp,
       String eol,
-      Function getNodeText,
-      Function getLinePrefix,
-      Function getIndent,
-      Function getText,
-      Function rangeNode) {
+      String Function(Expression) getNodeText,
+      String Function(int) getLinePrefix,
+      String Function(int) getIndent,
+      String Function(int, int) getText,
+      SourceRange Function(Expression) rangeNode) {
     var childLoc = namedExp.offset + 'child'.length;
     builder.addSimpleInsertion(childLoc, 'ren');
     var listLoc = childArg.offset;
-    String childArgSrc = getNodeText(childArg);
+    var childArgSrc = getNodeText(childArg);
     if (!childArgSrc.contains(eol)) {
       builder.addSimpleInsertion(listLoc, '[');
       builder.addSimpleInsertion(listLoc + childArg.length, ']');
@@ -138,11 +94,10 @@
       if (newlineLoc == childArgSrc.length) {
         newlineLoc -= 1;
       }
-      String indentOld =
-          getLinePrefix(childArg.offset + eol.length + newlineLoc);
+      var indentOld = getLinePrefix(childArg.offset + eol.length + newlineLoc);
       var indentNew = '$indentOld${getIndent(1)}';
       // The separator includes 'child:' but that has no newlines.
-      String separator =
+      var separator =
           getText(namedExp.offset, childArg.offset - namedExp.offset);
       var prefix = separator.contains(eol) ? '' : '$eol$indentNew';
       if (prefix.isEmpty) {
diff --git a/pkg/analysis_server/test/services/completion/dart/arglist_contributor_test.dart b/pkg/analysis_server/test/services/completion/dart/arglist_contributor_test.dart
index 4c2e182..c2d8833 100644
--- a/pkg/analysis_server/test/services/completion/dart/arglist_contributor_test.dart
+++ b/pkg/analysis_server/test/services/completion/dart/arglist_contributor_test.dart
@@ -172,6 +172,15 @@
     assertSuggestArgumentsAndTypes(namedArgumentsWithTypes: {'one': 'int'});
   }
 
+  Future<void> test_Annotation_local_constructor_named_param_12() async {
+    addTestSource('''
+class A { const A(int one, int two, int three, {int four, String five:
+  'defaultValue'}); }
+@A(1, ^, 3) main() { }''');
+    await computeSuggestions();
+    assertSuggestions(['four: ', 'five: ']);
+  }
+
   Future<void> test_Annotation_local_constructor_named_param_2() async {
     addTestSource('''
 class A { const A({int one, String two: 'defaultValue'}); }
@@ -239,6 +248,7 @@
 
   Future<void> test_Annotation_local_constructor_named_param_negative() async {
     addTestSource('''
+// @dart = 2.15
 class A { const A(int one, int two, int three, {int four, String five:
   'defaultValue'}); }
 @A(1, ^, 3) main() { }''');
@@ -660,6 +670,7 @@
       expect(String arg1, int arg2, {bool arg3}) { }
       void baz() { }''');
     addTestSource('''
+      // @dart = 2.15
       import 'a.dart'
       class B { }
       String bar() => true;
@@ -676,6 +687,7 @@
       expect(String arg1, int arg2, {bool arg3}) { }
       void baz() { }''');
     addTestSource('''
+      // @dart = 2.15
       import 'a.dart'
       class B { }
       String bar() => true;
@@ -692,6 +704,7 @@
       expect(String arg1, int arg2, {bool arg3}) { }
       void baz() { }''');
     addTestSource('''
+      // @dart = 2.15
       import 'a.dart'
       class B { }
       String bar() => true;
@@ -708,6 +721,7 @@
       expect(String arg1, int arg2, {bool arg3}) { }
       void baz() { }''');
     addTestSource('''
+      // @dart = 2.15
       import 'a.dart'
       class B { }
       String bar() => true;
@@ -987,6 +1001,7 @@
   Future<void> test_ArgumentList_local_function_3a() async {
     // ArgumentList  MethodInvocation  ExpressionStatement  Block
     addTestSource('''
+      // @dart = 2.15
       expect(arg1, int arg2, {bool arg3}) { }
       class B { }
       String bar() => true;
@@ -998,6 +1013,7 @@
   Future<void> test_ArgumentList_local_function_3b() async {
     // ArgumentList  MethodInvocation  ExpressionStatement  Block
     addTestSource('''
+      // @dart = 2.15
       expect(arg1, int arg2, {bool arg3}) { }
       class B { }
       String bar() => true;
@@ -1009,6 +1025,7 @@
   Future<void> test_ArgumentList_local_function_3c() async {
     // ArgumentList  MethodInvocation  ExpressionStatement  Block
     addTestSource('''
+      // @dart = 2.15
       expect(arg1, int arg2, {bool arg3}) { }
       class B { }
       String bar() => true;
@@ -1020,6 +1037,7 @@
   Future<void> test_ArgumentList_local_function_3d() async {
     // ArgumentList  MethodInvocation  ExpressionStatement  Block
     addTestSource('''
+      // @dart = 2.15
       expect(arg1, int arg2, {bool arg3}) { }
       class B { }
       String bar() => true;
diff --git a/pkg/analysis_server/test/src/services/correction/fix/fix_processor.dart b/pkg/analysis_server/test/src/services/correction/fix/fix_processor.dart
index 50411cb..a929b5e 100644
--- a/pkg/analysis_server/test/src/services/correction/fix/fix_processor.dart
+++ b/pkg/analysis_server/test/src/services/correction/fix/fix_processor.dart
@@ -264,8 +264,7 @@
 
   Future<void> addUnimportedFile(String filePath, String content) async {
     addSource(filePath, content);
-    var result = await session.getResolvedUnit(convertPath(filePath));
-    extensionCache.cacheFromResult(result as ResolvedUnitResult);
+    await cacheExtensionsForFile(filePath);
   }
 
   Future<void> assertHasFix(String expected,
@@ -378,6 +377,11 @@
     await _assertNoFixAllFix(error);
   }
 
+  Future<void> cacheExtensionsForFile(String path) async {
+    var result = await session.getResolvedUnit(convertPath(path));
+    extensionCache.cacheFromResult(result as ResolvedUnitResult);
+  }
+
   List<LinkedEditSuggestion> expectedSuggestions(
       LinkedEditSuggestionKind kind, List<String> values) {
     return values.map((value) {
diff --git a/pkg/analysis_server/test/src/services/correction/fix/import_library_project_test.dart b/pkg/analysis_server/test/src/services/correction/fix/import_library_project_test.dart
index a677f3a..be2de8f 100644
--- a/pkg/analysis_server/test/src/services/correction/fix/import_library_project_test.dart
+++ b/pkg/analysis_server/test/src/services/correction/fix/import_library_project_test.dart
@@ -234,6 +234,48 @@
 ''');
   }
 
+  @FailingTest(reason: 'We suggest importing src/b.dart')
+  Future<void> test_extension_otherPackage_exported_fromSrc() async {
+    var pkgRootPath = '/.pub-cache/aaa';
+
+    var a = newFile('$pkgRootPath/lib/a.dart', content: r'''
+export 'src/b.dart';
+''');
+
+    var b = newFile('$pkgRootPath/lib/src/b.dart', content: r'''
+extension IntExtension on int {
+  int get foo => 0;
+}
+''');
+
+    writeTestPackageConfig(
+      config: PackageConfigFileBuilder()
+        ..add(name: 'aaa', rootPath: pkgRootPath),
+    );
+
+    updateTestPubspecFile('''
+dependencies:
+  aaa: any
+''');
+
+    await cacheExtensionsForFile(a.path);
+    await cacheExtensionsForFile(b.path);
+
+    await resolveTestCode('''
+void f() {
+  0.foo;
+}
+''');
+
+    await assertHasFix('''
+import 'package:aaa/a.dart';
+
+void f() {
+  0.foo;
+}
+''');
+  }
+
   Future<void> test_invalidUri_interpolation() async {
     addSource('$testPackageLibPath/lib.dart', r'''
 class Test {
diff --git a/pkg/analyzer/lib/dart/ast/ast.dart b/pkg/analyzer/lib/dart/ast/ast.dart
index a376881..bf9af56 100644
--- a/pkg/analyzer/lib/dart/ast/ast.dart
+++ b/pkg/analyzer/lib/dart/ast/ast.dart
@@ -1577,7 +1577,9 @@
 /// The declaration of an enumeration.
 ///
 ///    enumType ::=
-///        metadata 'enum' [SimpleIdentifier] '{' [SimpleIdentifier] (',' [SimpleIdentifier])* (',')? '}'
+///        metadata 'enum' [SimpleIdentifier] [TypeParameterList]?
+///        [WithClause]? [ImplementsClause]? '{' [SimpleIdentifier]
+///        (',' [SimpleIdentifier])* (';' [ClassMember]+)? '}'
 ///
 /// Clients may not extend, implement or mix-in this class.
 abstract class EnumDeclaration implements NamedCompilationUnitMember {
@@ -1590,6 +1592,10 @@
   /// Return the 'enum' keyword.
   Token get enumKeyword;
 
+  /// Returns the `implements` clause for the enumeration, or `null` if the
+  /// enumeration does not implement any interfaces.
+  ImplementsClause? get implementsClause;
+
   /// Return the left curly bracket.
   Token get leftBracket;
 
@@ -1601,6 +1607,14 @@
 
   /// Return the right curly bracket.
   Token get rightBracket;
+
+  /// Returns the type parameters for the enumeration, or `null` if the
+  /// enumeration does not have any type parameters.
+  TypeParameterList? get typeParameters;
+
+  /// Return the `with` clause for the enumeration, or `null` if the
+  /// enumeration does not have a `with` clause.
+  WithClause? get withClause;
 }
 
 /// An export directive.
diff --git a/pkg/analyzer/lib/dart/ast/ast_factory.dart b/pkg/analyzer/lib/dart/ast/ast_factory.dart
index f4c31cb..29187a7 100644
--- a/pkg/analyzer/lib/dart/ast/ast_factory.dart
+++ b/pkg/analyzer/lib/dart/ast/ast_factory.dart
@@ -301,6 +301,7 @@
   /// [comment] and [metadata] can be `null` if the declaration does not have
   /// the corresponding attribute. The list of [constants] must contain at least
   /// one value.
+  @Deprecated('Use enumDeclaration2() instead')
   EnumDeclaration enumDeclaration(
       Comment? comment,
       List<Annotation>? metadata,
@@ -308,9 +309,26 @@
       SimpleIdentifier name,
       Token leftBracket,
       List<EnumConstantDeclaration> constants,
-      List<ClassMember> members,
       Token rightBracket);
 
+  /// Returns a newly created enumeration declaration. Either or both of the
+  /// [comment] and [metadata] can be `null` if the declaration does not have
+  /// the corresponding attribute. The list of [constants] must contain at least
+  /// one value.
+  EnumDeclaration enumDeclaration2({
+    required Comment? comment,
+    required List<Annotation>? metadata,
+    required Token enumKeyword,
+    required SimpleIdentifier name,
+    required TypeParameterList? typeParameters,
+    required WithClause? withClause,
+    required ImplementsClause? implementsClause,
+    required Token leftBracket,
+    required List<EnumConstantDeclaration> constants,
+    required List<ClassMember> members,
+    required Token rightBracket,
+  });
+
   /// Returns a newly created export directive. Either or both of the
   /// [comment] and [metadata] can be `null` if the directive does not have the
   /// corresponding attribute. The list of [combinators] can be `null` if there
diff --git a/pkg/analyzer/lib/src/dart/analysis/file_state.dart b/pkg/analyzer/lib/src/dart/analysis/file_state.dart
index 532447a..2c3364c 100644
--- a/pkg/analyzer/lib/src/dart/analysis/file_state.dart
+++ b/pkg/analyzer/lib/src/dart/analysis/file_state.dart
@@ -873,7 +873,7 @@
 
       File resource = _resourceProvider.getFile(path);
 
-      var rewrittenUri = rewriteFileToPackageUri(_sourceFactory, uri);
+      var rewrittenUri = rewriteToCanonicalUri(_sourceFactory, uri);
       if (rewrittenUri == null) {
         return Either2.t1(null);
       }
diff --git a/pkg/analyzer/lib/src/dart/analysis/library_analyzer.dart b/pkg/analyzer/lib/src/dart/analysis/library_analyzer.dart
index beabb03..ce3f0b2 100644
--- a/pkg/analyzer/lib/src/dart/analysis/library_analyzer.dart
+++ b/pkg/analyzer/lib/src/dart/analysis/library_analyzer.dart
@@ -783,7 +783,7 @@
     }
 
     var absoluteUri = resolveRelativeUri(_library.uri, relativeUri);
-    return rewriteFileToPackageUri(_sourceFactory, absoluteUri);
+    return rewriteToCanonicalUri(_sourceFactory, absoluteUri);
   }
 
   /// Return the result of resolve the given [uriContent], reporting errors
diff --git a/pkg/analyzer/lib/src/dart/ast/ast.dart b/pkg/analyzer/lib/src/dart/ast/ast.dart
index 3ab0730..176f6e4 100644
--- a/pkg/analyzer/lib/src/dart/ast/ast.dart
+++ b/pkg/analyzer/lib/src/dart/ast/ast.dart
@@ -3286,14 +3286,27 @@
 /// The declaration of an enumeration.
 ///
 ///    enumType ::=
-///        metadata 'enum' [SimpleIdentifier] '{' [SimpleIdentifier]
-///        (',' [SimpleIdentifier])* (',')? '}'
+///        metadata 'enum' [SimpleIdentifier] [TypeParameterList]?
+///        [WithClause]? [ImplementsClause]? '{' [SimpleIdentifier]
+///        (',' [SimpleIdentifier])* (';' [ClassMember]+)? '}'
 class EnumDeclarationImpl extends NamedCompilationUnitMemberImpl
     implements EnumDeclaration {
   /// The 'enum' keyword.
   @override
   Token enumKeyword;
 
+  /// The type parameters, or `null` if the enumeration does not have any
+  /// type parameters.
+  TypeParameterListImpl? _typeParameters;
+
+  /// The `with` clause for the enumeration, or `null` if the class does not
+  /// have a `with` clause.
+  WithClauseImpl? _withClause;
+
+  /// The `implements` clause for the enumeration, or `null` if the enumeration
+  /// does not implement any interfaces.
+  ImplementsClauseImpl? _implementsClause;
+
   /// The left curly bracket.
   @override
   Token leftBracket;
@@ -3317,11 +3330,17 @@
       List<Annotation>? metadata,
       this.enumKeyword,
       SimpleIdentifierImpl name,
+      this._typeParameters,
+      this._withClause,
+      this._implementsClause,
       this.leftBracket,
       List<EnumConstantDeclaration> constants,
       List<ClassMember> members,
       this.rightBracket)
       : super(comment, metadata, name) {
+    _becomeParentOf(_typeParameters);
+    _becomeParentOf(_withClause);
+    _becomeParentOf(_implementsClause);
     _constants._initialize(this, constants);
     _members._initialize(this, members);
   }
@@ -3331,6 +3350,9 @@
   Iterable<SyntacticEntity> get childEntities => super._childEntities
     ..add(enumKeyword)
     ..add(_name)
+    ..add(_typeParameters)
+    ..add(_withClause)
+    ..add(_implementsClause)
     ..add(leftBracket)
     ..addAll(_constants)
     ..addAll(_members)
@@ -3349,15 +3371,40 @@
   Token get firstTokenAfterCommentAndMetadata => enumKeyword;
 
   @override
+  ImplementsClauseImpl? get implementsClause => _implementsClause;
+
+  set implementsClause(ImplementsClause? implementsClause) {
+    _implementsClause =
+        _becomeParentOf(implementsClause as ImplementsClauseImpl?);
+  }
+
+  @override
   NodeListImpl<ClassMember> get members => _members;
 
   @override
+  TypeParameterListImpl? get typeParameters => _typeParameters;
+
+  set typeParameters(TypeParameterList? typeParameters) {
+    _typeParameters = _becomeParentOf(typeParameters as TypeParameterListImpl?);
+  }
+
+  @override
+  WithClauseImpl? get withClause => _withClause;
+
+  set withClause(WithClause? withClause) {
+    _withClause = _becomeParentOf(withClause as WithClauseImpl?);
+  }
+
+  @override
   E? accept<E>(AstVisitor<E> visitor) => visitor.visitEnumDeclaration(this);
 
   @override
   void visitChildren(AstVisitor visitor) {
     super.visitChildren(visitor);
     _name.accept(visitor);
+    _typeParameters?.accept(visitor);
+    _withClause?.accept(visitor);
+    _implementsClause?.accept(visitor);
     _constants.accept(visitor);
     _members.accept(visitor);
   }
diff --git a/pkg/analyzer/lib/src/dart/ast/ast_factory.dart b/pkg/analyzer/lib/src/dart/ast/ast_factory.dart
index b7a9b76..e1f0415 100644
--- a/pkg/analyzer/lib/src/dart/ast/ast_factory.dart
+++ b/pkg/analyzer/lib/src/dart/ast/ast_factory.dart
@@ -383,6 +383,7 @@
       EnumConstantDeclarationImpl(
           comment as CommentImpl?, metadata, name as SimpleIdentifierImpl);
 
+  @Deprecated('Use enumDeclaration2() instead')
   @override
   EnumDeclarationImpl enumDeclaration(
           Comment? comment,
@@ -391,17 +392,48 @@
           SimpleIdentifier name,
           Token leftBracket,
           List<EnumConstantDeclaration> constants,
-          List<ClassMember> members,
           Token rightBracket) =>
-      EnumDeclarationImpl(
-          comment as CommentImpl?,
-          metadata,
-          enumKeyword,
-          name as SimpleIdentifierImpl,
-          leftBracket,
-          constants,
-          members,
-          rightBracket);
+      enumDeclaration2(
+          comment: comment,
+          metadata: metadata,
+          enumKeyword: enumKeyword,
+          name: name,
+          typeParameters: null,
+          withClause: null,
+          implementsClause: null,
+          leftBracket: leftBracket,
+          constants: constants,
+          members: [],
+          rightBracket: rightBracket);
+
+  @override
+  EnumDeclarationImpl enumDeclaration2({
+    required Comment? comment,
+    required List<Annotation>? metadata,
+    required Token enumKeyword,
+    required SimpleIdentifier name,
+    required TypeParameterList? typeParameters,
+    required WithClause? withClause,
+    required ImplementsClause? implementsClause,
+    required Token leftBracket,
+    required List<EnumConstantDeclaration> constants,
+    required List<ClassMember> members,
+    required Token rightBracket,
+  }) {
+    return EnumDeclarationImpl(
+      comment as CommentImpl?,
+      metadata,
+      enumKeyword,
+      name as SimpleIdentifierImpl,
+      typeParameters as TypeParameterListImpl?,
+      withClause as WithClauseImpl?,
+      implementsClause as ImplementsClauseImpl?,
+      leftBracket,
+      constants,
+      members,
+      rightBracket,
+    );
+  }
 
   @override
   ExportDirectiveImpl exportDirective(
diff --git a/pkg/analyzer/lib/src/dart/ast/to_source_visitor.dart b/pkg/analyzer/lib/src/dart/ast/to_source_visitor.dart
index 49dff85..d31ae43 100644
--- a/pkg/analyzer/lib/src/dart/ast/to_source_visitor.dart
+++ b/pkg/analyzer/lib/src/dart/ast/to_source_visitor.dart
@@ -314,8 +314,12 @@
     _visitNodeList(node.metadata, separator: ' ', suffix: ' ');
     sink.write('enum ');
     _visitNode(node.name);
+    _visitNode(node.typeParameters);
+    _visitNode(node.withClause, prefix: ' ');
+    _visitNode(node.implementsClause, prefix: ' ');
     sink.write(' {');
     _visitNodeList(node.constants, separator: ', ');
+    _visitNodeList(node.members, prefix: '; ', separator: ' ');
     sink.write('}');
   }
 
diff --git a/pkg/analyzer/lib/src/dart/ast/utilities.dart b/pkg/analyzer/lib/src/dart/ast/utilities.dart
index 3bbe4f6..308fad828 100644
--- a/pkg/analyzer/lib/src/dart/ast/utilities.dart
+++ b/pkg/analyzer/lib/src/dart/ast/utilities.dart
@@ -2002,8 +2002,19 @@
     if (identical(node.name, _oldNode)) {
       node.name = _newNode as SimpleIdentifier;
       return true;
+    } else if (identical(node.typeParameters, _oldNode)) {
+      node.typeParameters = _newNode as TypeParameterList;
+      return true;
+    } else if (identical(node.withClause, _oldNode)) {
+      node.withClause = _newNode as WithClause;
+      return true;
+    } else if (identical(node.implementsClause, _oldNode)) {
+      node.implementsClause = _newNode as ImplementsClause;
+      return true;
     } else if (_replaceInList(node.constants)) {
       return true;
+    } else if (_replaceInList(node.members)) {
+      return true;
     }
     return visitAnnotatedNode(node);
   }
diff --git a/pkg/analyzer/lib/src/fasta/ast_builder.dart b/pkg/analyzer/lib/src/fasta/ast_builder.dart
index 6cfd05b..dea89e7 100644
--- a/pkg/analyzer/lib/src/fasta/ast_builder.dart
+++ b/pkg/analyzer/lib/src/fasta/ast_builder.dart
@@ -2813,8 +2813,21 @@
       );
     }
 
-    declarations.add(enumDeclaration = ast.enumDeclaration(comment, metadata,
-        enumKeyword, name, leftBrace, [], [], leftBrace.endGroup!));
+    declarations.add(
+      enumDeclaration = ast.enumDeclaration2(
+        comment: comment,
+        metadata: metadata,
+        enumKeyword: enumKeyword,
+        name: name,
+        typeParameters: typeParameters,
+        withClause: withClause,
+        implementsClause: implementsClause,
+        leftBracket: leftBrace,
+        constants: [],
+        members: [],
+        rightBracket: leftBrace.endGroup!,
+      ),
+    );
   }
 
   @override
diff --git a/pkg/analyzer/lib/src/generated/testing/ast_test_factory.dart b/pkg/analyzer/lib/src/generated/testing/ast_test_factory.dart
index e05cbc0..fec2395 100644
--- a/pkg/analyzer/lib/src/generated/testing/ast_test_factory.dart
+++ b/pkg/analyzer/lib/src/generated/testing/ast_test_factory.dart
@@ -458,30 +458,6 @@
   static EmptyStatementImpl emptyStatement() => astFactory
       .emptyStatement(TokenFactory.tokenFromType(TokenType.SEMICOLON));
 
-  static EnumDeclarationImpl enumDeclaration(
-          SimpleIdentifier name, List<EnumConstantDeclaration> constants) =>
-      astFactory.enumDeclaration(
-          null,
-          null,
-          TokenFactory.tokenFromKeyword(Keyword.ENUM),
-          name,
-          TokenFactory.tokenFromType(TokenType.OPEN_CURLY_BRACKET),
-          constants,
-          [],
-          TokenFactory.tokenFromType(TokenType.CLOSE_CURLY_BRACKET));
-
-  static EnumDeclarationImpl enumDeclaration2(
-      String name, List<String> constantNames) {
-    var constants = constantNames.map((name) {
-      return astFactory.enumConstantDeclaration(
-        null,
-        null,
-        identifier3(name),
-      );
-    }).toList();
-    return enumDeclaration(identifier3(name), constants);
-  }
-
   static ExportDirectiveImpl exportDirective(
           List<Annotation> metadata, String uri,
           [List<Combinator> combinators = const []]) =>
diff --git a/pkg/analyzer/lib/src/lint/pub.dart b/pkg/analyzer/lib/src/lint/pub.dart
index 8c11a57..be9b149 100644
--- a/pkg/analyzer/lib/src/lint/pub.dart
+++ b/pkg/analyzer/lib/src/lint/pub.dart
@@ -37,6 +37,12 @@
 
 PSGitRepo? _processGitRepo(
     YamlScalar key, YamlNode v, ResourceProvider? resourceProvider) {
+  if (v is YamlScalar) {
+    _PSGitRepo repo = _PSGitRepo();
+    repo.token = _PSNode(key, resourceProvider);
+    repo.url = PSEntry(repo.token, _PSNode(v, resourceProvider));
+    return repo;
+  }
   if (v is! YamlMap) {
     return null;
   }
@@ -130,9 +136,44 @@
   String toString() => '${key != null ? (key.toString() + ': ') : ''}$value';
 }
 
+/// Representation of git-dependency in `pubspec.yaml`.
+///
+/// **Example** of a git-dependency:
+/// ```yaml
+/// dependencies:
+///   foo:
+///     git: # <-- this is the [token] property
+///       url: https://github.com/example/example
+///       ref: main # ref is optional
+/// ```
+///
+/// This may also be written in the form:
+/// ```yaml
+/// dependencies:
+///   foo:
+///     git:       https://github.com/example/example
+///     # ^-token  ^--url
+///     # In this case [ref] is `null`.
+/// ```
 abstract class PSGitRepo {
+  /// [PSEntry] for `ref: main` where [PSEntry.key] is `ref` and [PSEntry.value]
+  /// is `main`.
   PSEntry? get ref;
+
+  /// The `'git'` from the `pubspec.yaml`, this is the key that indicates this
+  /// is a git-dependency.
   PSNode? get token;
+
+  /// [PSEntry] for `url: https://...` or `git: https://`, where [PSEntry.key]
+  /// is either `url` or `git`, and [PSEntry.key] is the URL.
+  ///
+  /// If the git-dependency is given in the form:
+  /// ```yaml
+  /// dependencies:
+  ///   foo:
+  ///     git:       https://github.com/example/example
+  /// ```
+  /// Then [token] and [url.key] will be the same object.
   PSEntry? get url;
 }
 
diff --git a/pkg/analyzer/lib/src/summary2/element_builder.dart b/pkg/analyzer/lib/src/summary2/element_builder.dart
index 8d6599b..af3cdb7 100644
--- a/pkg/analyzer/lib/src/summary2/element_builder.dart
+++ b/pkg/analyzer/lib/src/summary2/element_builder.dart
@@ -1009,7 +1009,7 @@
     var absoluteUri = resolveRelativeUri(_libraryBuilder.uri, relativeUri);
 
     var sourceFactory = _linker.analysisContext.sourceFactory;
-    return rewriteFileToPackageUri(sourceFactory, absoluteUri);
+    return rewriteToCanonicalUri(sourceFactory, absoluteUri);
   }
 
   LibraryElement? _selectLibrary(NamespaceDirective node) {
diff --git a/pkg/analyzer/lib/src/test_utilities/find_node.dart b/pkg/analyzer/lib/src/test_utilities/find_node.dart
index 3c22e00..a248815 100644
--- a/pkg/analyzer/lib/src/test_utilities/find_node.dart
+++ b/pkg/analyzer/lib/src/test_utilities/find_node.dart
@@ -123,6 +123,10 @@
     return _node(search, (n) => n is DoubleLiteral);
   }
 
+  EnumConstantDeclaration enumConstantDeclaration(String search) {
+    return _node(search, (n) => n is EnumConstantDeclaration);
+  }
+
   EnumDeclaration enumDeclaration(String search) {
     return _node(search, (n) => n is EnumDeclaration);
   }
diff --git a/pkg/analyzer/lib/src/util/uri.dart b/pkg/analyzer/lib/src/util/uri.dart
index 08e3008..4d60895 100644
--- a/pkg/analyzer/lib/src/util/uri.dart
+++ b/pkg/analyzer/lib/src/util/uri.dart
@@ -13,23 +13,10 @@
   return path;
 }
 
-/// If the [absoluteUri] is a `file` URI that has corresponding `package` URI,
-/// return it. If the URI is not valid, e.g. has empty path segments, so
-/// does not represent a valid file path, return `null`.
-Uri? rewriteFileToPackageUri(SourceFactory sourceFactory, Uri absoluteUri) {
-  // Only file URIs get rewritten into package URIs.
-  if (!absoluteUri.isScheme('file')) {
-    return absoluteUri;
-  }
-
-  // It must be a valid URI, e.g. `file:///home/` is not.
-  var pathSegments = absoluteUri.pathSegments;
-  if (pathSegments.isEmpty || pathSegments.last.isEmpty) {
-    return null;
-  }
-
-  // We ask for Source only because `restoreUri` needs it.
-  // TODO(scheglov) Add more direct way to convert a path to URI.
+/// Return the canonical URI for the given [absoluteUri], for example a `file`
+/// URI to the corresponding `package` URI. If the URI is not valid, so does
+/// not represent a valid file path, return `null`.
+Uri? rewriteToCanonicalUri(SourceFactory sourceFactory, Uri absoluteUri) {
   var source = sourceFactory.forUri2(absoluteUri);
   if (source == null) {
     return null;
diff --git a/pkg/analyzer/test/generated/utilities_test.dart b/pkg/analyzer/test/generated/utilities_test.dart
index b4ff551..348bd17 100644
--- a/pkg/analyzer/test/generated/utilities_test.dart
+++ b/pkg/analyzer/test/generated/utilities_test.dart
@@ -1649,12 +1649,44 @@
   }
 
   void test_enumDeclaration() {
-    var node = AstTestFactory.enumDeclaration2("E", ["ONE", "TWO"]);
-    node.documentationComment = astFactory.endOfLineComment(EMPTY_TOKEN_LIST);
-    node.metadata
-        .add(AstTestFactory.annotation(AstTestFactory.identifier3("a")));
-    _assertReplace(node, Getter_NodeReplacerTest_test_enumDeclaration());
-    _testAnnotatedNode(node);
+    var findNode = _parseStringToFindNode(r'''
+enum E1<T> with M1 implements I1 {one, two}
+enum E2<U> with M2 implements I2 {one, two}
+''');
+    _assertReplace2<EnumDeclaration>(
+      destination: findNode.enumDeclaration('enum E1'),
+      source: findNode.enumDeclaration('enum E2'),
+      getters: [
+        (node) => node.name,
+        (node) => node.typeParameters!,
+        (node) => node.withClause!,
+        (node) => node.implementsClause!,
+      ],
+    );
+  }
+
+  void test_enumDeclaration_constants() {
+    var findNode = _parseStringToFindNode(r'''
+enum E1 {one}
+enum E2 {two}
+''');
+    _assertReplaceInList(
+      destination: findNode.enumDeclaration('enum E1'),
+      child: findNode.enumConstantDeclaration('one'),
+      replacement: findNode.enumConstantDeclaration('two'),
+    );
+  }
+
+  void test_enumDeclaration_members() {
+    var findNode = _parseStringToFindNode(r'''
+enum E1 {one; void foo() {}}
+enum E2 {two; void bar() {}}
+''');
+    _assertReplaceInList(
+      destination: findNode.enumDeclaration('enum E1'),
+      child: findNode.methodDeclaration('foo'),
+      replacement: findNode.methodDeclaration('bar'),
+    );
   }
 
   void test_exportDirective() {
@@ -2303,12 +2335,24 @@
     }
   }
 
+  void _assertReplaceInList({
+    required AstNode destination,
+    required AstNode child,
+    required AstNode replacement,
+  }) {
+    expect(child.parent, destination);
+
+    NodeReplacer.replace(child, replacement);
+    expect(replacement.parent, destination);
+  }
+
   FindNode _parseStringToFindNode(String content) {
     var parseResult = parseString(
       content: content,
       featureSet: FeatureSet.fromEnableFlags2(
         sdkLanguageVersion: ExperimentStatus.currentVersion,
         flags: [
+          Feature.enhanced_enums.enableString,
           Feature.super_parameters.enableString,
         ],
       ),
diff --git a/pkg/analyzer/test/src/dart/analysis/driver_test.dart b/pkg/analyzer/test/src/dart/analysis/driver_test.dart
index 252bab2..8568ee0 100644
--- a/pkg/analyzer/test/src/dart/analysis/driver_test.dart
+++ b/pkg/analyzer/test/src/dart/analysis/driver_test.dart
@@ -28,12 +28,14 @@
 
 import '../../../util/element_type_matchers.dart';
 import '../../../utils.dart';
+import '../resolution/context_collection_resolution.dart';
 import 'base.dart';
 
 main() {
   defineReflectiveSuite(() {
     defineReflectiveTests(AnalysisDriverSchedulerTest);
     defineReflectiveTests(AnalysisDriverTest);
+    defineReflectiveTests(AnalysisDriver_BazelWorkspaceTest);
   });
 }
 
@@ -50,6 +52,59 @@
 }
 
 @reflectiveTest
+class AnalysisDriver_BazelWorkspaceTest extends BazelWorkspaceResolutionTest {
+  void test_nestedLib_notCanonicalUri() async {
+    var outerLibPath = '$workspaceRootPath/my/outer/lib';
+
+    var innerPath = convertPath('$outerLibPath/inner/lib/b.dart');
+    var innerUri = Uri.parse('package:my.outer.lib.inner/b.dart');
+    newFile(innerPath, content: 'class B {}');
+
+    var analysisSession = contextFor(innerPath).currentSession;
+
+    void assertInnerUri(ResolvedUnitResult result) {
+      var innerLibrary = result.libraryElement.importedLibraries
+          .where((e) => e.source.fullName == innerPath)
+          .single;
+      expect(innerLibrary.source.uri, innerUri);
+    }
+
+    // Reference "inner" using a non-canonical URI.
+    {
+      var path = convertPath('$outerLibPath/a.dart');
+      newFile(path, content: r'''
+import 'inner/lib/b.dart';
+''');
+      var result = await analysisSession.getResolvedUnit(path);
+      result as ResolvedUnitResult;
+      assertInnerUri(result);
+    }
+
+    // Reference "inner" using the canonical URI, via relative.
+    {
+      var path = '$outerLibPath/inner/lib/c.dart';
+      newFile(path, content: r'''
+import 'b.dart';
+''');
+      var result = await analysisSession.getResolvedUnit(path);
+      result as ResolvedUnitResult;
+      assertInnerUri(result);
+    }
+
+    // Reference "inner" using the canonical URI, via absolute.
+    {
+      var path = '$outerLibPath/inner/lib/d.dart';
+      newFile(path, content: '''
+import '$innerUri';
+''');
+      var result = await analysisSession.getResolvedUnit(path);
+      result as ResolvedUnitResult;
+      assertInnerUri(result);
+    }
+  }
+}
+
+@reflectiveTest
 class AnalysisDriverSchedulerTest with ResourceProviderMixin {
   final ByteStore byteStore = MemoryByteStore();
 
diff --git a/pkg/analyzer/test/src/dart/analysis/file_state_test.dart b/pkg/analyzer/test/src/dart/analysis/file_state_test.dart
index f0a3e1f..539ff59 100644
--- a/pkg/analyzer/test/src/dart/analysis/file_state_test.dart
+++ b/pkg/analyzer/test/src/dart/analysis/file_state_test.dart
@@ -92,6 +92,26 @@
     expect(generatedFile.path, generatedPath);
     expect(writableFile2, same(generatedFile));
   }
+
+  void test_getFileForUri_nestedLib_notCanonicalUri() async {
+    var outerPath = convertPath('$workspaceRootPath/my/outer/lib/a.dart');
+    var outerUri = Uri.parse('package:my.outer/a.dart');
+
+    var innerPath = convertPath('/workspace/my/outer/lib/inner/lib/b.dart');
+    var innerUri = Uri.parse('package:my.outer.lib.inner/b.dart');
+
+    var analysisDriver = driverFor(outerPath);
+    var fsState = analysisDriver.fsState;
+
+    // User code might use such relative URI.
+    var innerUri2 = outerUri.resolve('inner/lib/b.dart');
+    expect(innerUri2, Uri.parse('package:my.outer/inner/lib/b.dart'));
+
+    // However the returned file must use the canonical URI.
+    var innerFile = fsState.getFileForUri(innerUri2).t1!;
+    expect(innerFile.path, innerPath);
+    expect(innerFile.uri, innerUri);
+  }
 }
 
 @reflectiveTest
diff --git a/pkg/analyzer/test/src/dart/ast/to_source_visitor_test.dart b/pkg/analyzer/test/src/dart/ast/to_source_visitor_test.dart
index 9914458..c686016 100644
--- a/pkg/analyzer/test/src/dart/ast/to_source_visitor_test.dart
+++ b/pkg/analyzer/test/src/dart/ast/to_source_visitor_test.dart
@@ -2,14 +2,17 @@
 // 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/features.dart';
 import 'package:analyzer/dart/analysis/utilities.dart';
 import 'package:analyzer/dart/ast/ast.dart';
 import 'package:analyzer/dart/ast/token.dart';
+import 'package:analyzer/src/dart/analysis/experiments.dart';
 import 'package:analyzer/src/dart/ast/ast_factory.dart';
 import 'package:analyzer/src/dart/ast/to_source_visitor.dart';
 import 'package:analyzer/src/generated/testing/ast_test_factory.dart';
 import 'package:analyzer/src/generated/testing/token_factory.dart';
 import 'package:analyzer/src/summary2/ast_binary_tokens.dart';
+import 'package:analyzer/src/test_utilities/find_node.dart';
 import 'package:test/test.dart';
 import 'package:test_reflective_loader/test_reflective_loader.dart';
 
@@ -765,14 +768,62 @@
     _assertSource(";", AstTestFactory.emptyStatement());
   }
 
-  void test_visitEnumDeclaration_multiple() {
-    _assertSource("enum E {ONE, TWO}",
-        AstTestFactory.enumDeclaration2("E", ["ONE", "TWO"]));
+  void test_visitEnumDeclaration_constants_multiple() {
+    var findNode = _parseStringToFindNode(r'''
+enum E {one, two}
+''');
+    _assertSource(
+      'enum E {one, two}',
+      findNode.enumDeclaration('E'),
+    );
   }
 
-  void test_visitEnumDeclaration_single() {
+  void test_visitEnumDeclaration_constants_single() {
+    var findNode = _parseStringToFindNode(r'''
+enum E {one}
+''');
     _assertSource(
-        "enum E {ONE}", AstTestFactory.enumDeclaration2("E", ["ONE"]));
+      'enum E {one}',
+      findNode.enumDeclaration('E'),
+    );
+  }
+
+  void test_visitEnumDeclaration_field_constructor() {
+    var findNode = _parseStringToFindNode(r'''
+enum E {
+  one, two;
+  final int field;
+  E(this.field);
+}
+''');
+    _assertSource(
+      'enum E {one, two; final int field; E(this.field);}',
+      findNode.enumDeclaration('enum E'),
+    );
+  }
+
+  void test_visitEnumDeclaration_method() {
+    var findNode = _parseStringToFindNode(r'''
+enum E {
+  one, two;
+  void myMethod() {}
+  int get myGetter => 0;
+}
+''');
+    _assertSource(
+      'enum E {one, two; void myMethod() {} int get myGetter => 0;}',
+      findNode.enumDeclaration('enum E'),
+    );
+  }
+
+  void test_visitEnumDeclaration_withoutMembers() {
+    var findNode = _parseStringToFindNode(r'''
+enum E<T> with M1, M2 implements I1, I2 {one, two}
+''');
+    _assertSource(
+      'enum E<T> with M1, M2 implements I1, I2 {one, two}',
+      findNode.enumDeclaration('E'),
+    );
   }
 
   void test_visitExportDirective_combinator() {
@@ -3356,4 +3407,18 @@
     node.accept(ToSourceVisitor(buffer));
     expect(buffer.toString(), expectedSource);
   }
+
+  FindNode _parseStringToFindNode(String content) {
+    var parseResult = parseString(
+      content: content,
+      featureSet: FeatureSet.fromEnableFlags2(
+        sdkLanguageVersion: ExperimentStatus.currentVersion,
+        flags: [
+          Feature.enhanced_enums.enableString,
+          Feature.super_parameters.enableString,
+        ],
+      ),
+    );
+    return FindNode(parseResult.content, parseResult.unit);
+  }
 }
diff --git a/pkg/analyzer/test/src/lint/pub_test.dart b/pkg/analyzer/test/src/lint/pub_test.dart
index db3a2d0..b5fbe2a 100644
--- a/pkg/analyzer/test/src/lint/pub_test.dart
+++ b/pkg/analyzer/test/src/lint/pub_test.dart
@@ -48,6 +48,8 @@
 dev_dependencies:
   markdown: '>=0.7.1+2 <0.8.0'
   unittest: '>=0.11.0 <0.12.0'
+  kittens2:
+    git: git://github.com/munificent/kittens2.git
 dependency_overrides:
   foo: 1.2.0
 repository: https://github.com/dart-lang/linter
@@ -148,6 +150,14 @@
         testValue(
             'url', git.url, equals('git://github.com/munificent/kittens.git'));
       });
+
+      group('git (short form)', () {
+        PSDependency dep = findDependency(ps.devDependencies, name: 'kittens2');
+        PSGitRepo git = dep.git!;
+        test('ref', () => expect(git.ref, isNull));
+        testValue(
+            'url', git.url, equals('git://github.com/munificent/kittens2.git'));
+      });
     });
 //    group('visiting', () {
 //      test('smoke', () {
diff --git a/pkg/analyzer/test/src/summary/resynthesize_ast2_test.dart b/pkg/analyzer/test/src/summary/resynthesize_ast2_test.dart
index 6378283..3c1a267 100644
--- a/pkg/analyzer/test/src/summary/resynthesize_ast2_test.dart
+++ b/pkg/analyzer/test/src/summary/resynthesize_ast2_test.dart
@@ -230,7 +230,7 @@
       }
 
       var absoluteUri = resolveRelativeUri(source.uri, relativeUri);
-      var rewrittenUri = rewriteFileToPackageUri(sourceFactory, absoluteUri);
+      var rewrittenUri = rewriteToCanonicalUri(sourceFactory, absoluteUri);
       if (rewrittenUri == null) {
         return;
       }
diff --git a/tools/VERSION b/tools/VERSION
index c66c69e..b2f9f59 100644
--- a/tools/VERSION
+++ b/tools/VERSION
@@ -27,5 +27,5 @@
 MAJOR 2
 MINOR 16
 PATCH 0
-PRERELEASE 84
+PRERELEASE 85
 PRERELEASE_PATCH 0
\ No newline at end of file