Add CommentReferableExpression, for expressions which can be used in a CommentReference

* Replace `identifier` field with `expression`, which means deprecating
  `identifier`, redirecting users to `expression`. For now, `expression`
  always returns an Identifier. In a future breaking release, it will
  return other CommentReferableExpressions.
* SimpleIdentifier, PrefixedIdentifier, PropertyAccess,
  ConstructorReference, FunctionReference, and TypeLiteral are all
  CommentReferableExpressions, but support is not implemented yet to
  parse CommentReferences with those contained expressions.

Bug: https://github.com/dart-lang/sdk/issues/47444
Change-Id: I1905afecf3878cd7dca6e275ef0a2ab80500eb4d
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/216320
Commit-Queue: Samuel Rawlins <srawlins@google.com>
Reviewed-by: Konstantin Shcheglov <scheglov@google.com>
Reviewed-by: Brian Wilkerson <brianwilkerson@google.com>
Reviewed-by: Janice Collins <jcollins@google.com>
diff --git a/pkg/analysis_server/lib/src/services/correction/dart/remove_deprecated_new_in_comment_reference.dart b/pkg/analysis_server/lib/src/services/correction/dart/remove_deprecated_new_in_comment_reference.dart
index 9c902e7..73c944b 100644
--- a/pkg/analysis_server/lib/src/services/correction/dart/remove_deprecated_new_in_comment_reference.dart
+++ b/pkg/analysis_server/lib/src/services/correction/dart/remove_deprecated_new_in_comment_reference.dart
@@ -40,18 +40,20 @@
       builder.addDeletion(range.startStart(newToken, newToken.next!));
     });
 
-    final identifier = comment.identifier;
-    final classElement = identifier.staticElement;
-    if (identifier is SimpleIdentifier && classElement is ConstructorElement) {
-      await builder.addDartFileEdit(file, (builder) {
-        builder.addSimpleInsertion(identifier.end, '.new');
-      });
-    } else {
-      if (classElement is ClassElement) {
-        if (classElement.unnamedConstructor != null) {
-          await builder.addDartFileEdit(file, (builder) {
-            builder.addSimpleInsertion(identifier.end, '.new');
-          });
+    final identifier = comment.expression;
+    if (identifier is Identifier) {
+      final element = identifier.staticElement;
+      if (identifier is SimpleIdentifier && element is ConstructorElement) {
+        await builder.addDartFileEdit(file, (builder) {
+          builder.addSimpleInsertion(identifier.end, '.new');
+        });
+      } else {
+        if (element is ClassElement) {
+          if (element.unnamedConstructor != null) {
+            await builder.addDartFileEdit(file, (builder) {
+              builder.addSimpleInsertion(identifier.end, '.new');
+            });
+          }
         }
       }
     }
diff --git a/pkg/analysis_server/tool/code_completion/code_metrics.dart b/pkg/analysis_server/tool/code_completion/code_metrics.dart
index 0ace057..da9d00b 100644
--- a/pkg/analysis_server/tool/code_completion/code_metrics.dart
+++ b/pkg/analysis_server/tool/code_completion/code_metrics.dart
@@ -343,7 +343,7 @@
   void visitCommentReference(CommentReference node) {
     _visitChildren(node, {
       'newKeyword': node.newKeyword,
-      'identifier': node.identifier,
+      'expression': node.expression,
     });
     super.visitCommentReference(node);
   }
diff --git a/pkg/analysis_server/tool/code_completion/relevance_metrics.dart b/pkg/analysis_server/tool/code_completion/relevance_metrics.dart
index a505521..e5ad8cc 100644
--- a/pkg/analysis_server/tool/code_completion/relevance_metrics.dart
+++ b/pkg/analysis_server/tool/code_completion/relevance_metrics.dart
@@ -478,7 +478,7 @@
       _recordTokenType(context, node);
     }
 
-    recordDataForCommentReference('CommentReference (name)', node.identifier);
+    recordDataForCommentReference('CommentReference (name)', node.expression);
     super.visitCommentReference(node);
   }
 
diff --git a/pkg/analysis_server/tool/code_completion/relevance_table_generator.dart b/pkg/analysis_server/tool/code_completion/relevance_table_generator.dart
index e3978af..30fd62f 100644
--- a/pkg/analysis_server/tool/code_completion/relevance_table_generator.dart
+++ b/pkg/analysis_server/tool/code_completion/relevance_table_generator.dart
@@ -479,7 +479,7 @@
 
   @override
   void visitCommentReference(CommentReference node) {
-    _recordDataForNode('CommentReference_identifier', node.identifier);
+    _recordDataForNode('CommentReference_expression', node.expression);
     super.visitCommentReference(node);
   }
 
diff --git a/pkg/analyzer/lib/dart/ast/ast.dart b/pkg/analyzer/lib/dart/ast/ast.dart
index b9efa0a..ba209b7 100644
--- a/pkg/analyzer/lib/dart/ast/ast.dart
+++ b/pkg/analyzer/lib/dart/ast/ast.dart
@@ -979,14 +979,33 @@
   List<Token> get tokens;
 }
 
+/// An interface for an [Expression] which can make up a [CommentReference].
+///
+///    commentReferableExpression ::=
+///        [ConstructorReference]
+///      | [FunctionReference]
+///      | [PrefixedIdentifier]
+///      | [PropertyAccess]
+///      | [SimpleIdentifier]
+///      | [TypeLiteral]
+///
+/// This interface should align closely with dartdoc's notion of
+/// comment-referable expressions at:
+/// https://github.com/dart-lang/dartdoc/blob/master/lib/src/comment_references/parser.dart
+abstract class CommentReferableExpression implements Expression {}
+
 /// A reference to a Dart element that is found within a documentation comment.
 ///
 ///    commentReference ::=
-///        '[' 'new'? [Identifier] ']'
+///        '[' 'new'? [CommentReferableExpression] ']'
 ///
 /// Clients may not extend, implement or mix-in this class.
 abstract class CommentReference implements AstNode {
+  /// The comment-referable expression being referenced.
+  CommentReferableExpression get expression;
+
   /// Return the identifier being referenced.
+  @Deprecated('Use expression instead')
   Identifier get identifier;
 
   /// Return the token representing the 'new' keyword, or `null` if there was no
@@ -1331,7 +1350,8 @@
 /// produced at resolution time.
 ///
 /// Clients may not extend, implement or mix-in this class.
-abstract class ConstructorReference implements Expression {
+abstract class ConstructorReference
+    implements Expression, CommentReferableExpression {
   /// The constructor being referenced.
   ConstructorName get constructorName;
 }
@@ -2319,7 +2339,8 @@
 /// arguments applied to it, e.g. the expression `print` in `var x = print;`.
 ///
 /// Clients may not extend, implement or mix-in this class.
-abstract class FunctionReference implements Expression {
+abstract class FunctionReference
+    implements Expression, CommentReferableExpression {
   /// The function being referenced.
   ///
   /// In error-free code, this will be either a SimpleIdentifier (indicating a
@@ -2503,7 +2524,7 @@
 ///      | [PrefixedIdentifier]
 ///
 /// Clients may not extend, implement or mix-in this class.
-abstract class Identifier implements Expression {
+abstract class Identifier implements Expression, CommentReferableExpression {
   /// Return the lexical representation of the identifier.
   String get name;
 
@@ -3588,7 +3609,8 @@
 ///        [Expression] '.' [SimpleIdentifier]
 ///
 /// Clients may not extend, implement or mix-in this class.
-abstract class PropertyAccess implements NullShortableExpression {
+abstract class PropertyAccess
+    implements NullShortableExpression, CommentReferableExpression {
   /// Return `true` if this expression is cascaded.
   ///
   /// If it is, then the target of this expression is not stored locally but is
@@ -4289,7 +4311,7 @@
 /// use `.typeName.type`.
 ///
 /// Clients may not extend, implement or mix-in this class.
-abstract class TypeLiteral implements Expression {
+abstract class TypeLiteral implements Expression, CommentReferableExpression {
   /// The type represented by this literal.
   NamedType get type;
 
diff --git a/pkg/analyzer/lib/dart/ast/ast_factory.dart b/pkg/analyzer/lib/dart/ast/ast_factory.dart
index baa41a5..8a714a8 100644
--- a/pkg/analyzer/lib/dart/ast/ast_factory.dart
+++ b/pkg/analyzer/lib/dart/ast/ast_factory.dart
@@ -158,7 +158,8 @@
 
   /// Returns a newly created reference to a Dart element. The [newKeyword]
   /// can be `null` if the reference is not to a constructor.
-  CommentReference commentReference(Token? newKeyword, Identifier identifier);
+  CommentReference commentReference(
+      Token? newKeyword, CommentReferableExpression expression);
 
   /// Returns a newly created compilation unit to have the given directives and
   /// declarations.  The [scriptTag] can be `null` (or omitted) if there is no
diff --git a/pkg/analyzer/lib/src/dart/analysis/index.dart b/pkg/analyzer/lib/src/dart/analysis/index.dart
index 5c8d8e7..e3b952f 100644
--- a/pkg/analyzer/lib/src/dart/analysis/index.dart
+++ b/pkg/analyzer/lib/src/dart/analysis/index.dart
@@ -579,21 +579,26 @@
 
   @override
   visitCommentReference(CommentReference node) {
-    var identifier = node.identifier;
-    var element = identifier.staticElement;
-    if (element is ConstructorElement) {
-      if (identifier is PrefixedIdentifier) {
-        var offset = identifier.prefix.end;
-        var length = identifier.end - offset;
-        recordRelationOffset(
-            element, IndexRelationKind.IS_REFERENCED_BY, offset, length, true);
-        return;
-      } else {
-        var offset = identifier.end;
-        recordRelationOffset(
-            element, IndexRelationKind.IS_REFERENCED_BY, offset, 0, true);
-        return;
+    var expression = node.expression;
+    if (expression is Identifier) {
+      var element = expression.staticElement;
+      if (element is ConstructorElement) {
+        if (expression is PrefixedIdentifier) {
+          var offset = expression.prefix.end;
+          var length = expression.end - offset;
+          recordRelationOffset(element, IndexRelationKind.IS_REFERENCED_BY,
+              offset, length, true);
+          return;
+        } else {
+          var offset = expression.end;
+          recordRelationOffset(
+              element, IndexRelationKind.IS_REFERENCED_BY, offset, 0, true);
+          return;
+        }
       }
+    } else {
+      throw UnimplementedError('Unhandled CommentReference expression type: '
+          '${expression.runtimeType}');
     }
 
     return super.visitCommentReference(node);
diff --git a/pkg/analyzer/lib/src/dart/ast/ast.dart b/pkg/analyzer/lib/src/dart/ast/ast.dart
index d9d000b..24e1241 100644
--- a/pkg/analyzer/lib/src/dart/ast/ast.dart
+++ b/pkg/analyzer/lib/src/dart/ast/ast.dart
@@ -1856,6 +1856,9 @@
       CommentImpl(tokens, CommentType.END_OF_LINE, const <CommentReference>[]);
 }
 
+abstract class CommentReferableExpressionImpl extends ExpressionImpl
+    implements CommentReferableExpression {}
+
 /// A reference to a Dart element that is found within a documentation comment.
 ///
 ///    commentReference ::=
@@ -1866,31 +1869,40 @@
   @override
   Token? newKeyword;
 
-  /// The identifier being referenced.
-  IdentifierImpl _identifier;
+  /// The expression being referenced.
+  CommentReferableExpressionImpl _expression;
 
   /// Initialize a newly created reference to a Dart element. The [newKeyword]
   /// can be `null` if the reference is not to a constructor.
-  CommentReferenceImpl(this.newKeyword, this._identifier) {
-    _becomeParentOf(_identifier);
+  CommentReferenceImpl(this.newKeyword, this._expression) {
+    _becomeParentOf(_expression);
   }
 
   @override
-  Token get beginToken => newKeyword ?? _identifier.beginToken;
+  Token get beginToken => newKeyword ?? _expression.beginToken;
 
   @override
   Iterable<SyntacticEntity> get childEntities => ChildEntities()
     ..add(newKeyword)
-    ..add(_identifier);
+    ..add(_expression);
 
   @override
-  Token get endToken => _identifier.endToken;
+  Token get endToken => _expression.endToken;
 
   @override
-  IdentifierImpl get identifier => _identifier;
+  CommentReferableExpression get expression => _expression;
 
+  set expression(CommentReferableExpression expression) {
+    _expression = _becomeParentOf(expression as CommentReferableExpressionImpl);
+  }
+
+  @override
+  @Deprecated('Use expression instead')
+  IdentifierImpl get identifier => _expression as IdentifierImpl;
+
+  @Deprecated('Use expression= instead')
   set identifier(Identifier identifier) {
-    _identifier = _becomeParentOf(identifier as IdentifierImpl);
+    _expression = _becomeParentOf(identifier as CommentReferableExpressionImpl);
   }
 
   @override
@@ -1898,7 +1910,7 @@
 
   @override
   void visitChildren(AstVisitor visitor) {
-    _identifier.accept(visitor);
+    _expression.accept(visitor);
   }
 }
 
@@ -2669,7 +2681,7 @@
 /// Objects of this type are not produced directly by the parser (because the
 /// parser cannot tell whether an identifier refers to a type); they are
 /// produced at resolution time.
-class ConstructorReferenceImpl extends ExpressionImpl
+class ConstructorReferenceImpl extends CommentReferableExpressionImpl
     implements ConstructorReference {
   ConstructorNameImpl _constructorName;
 
@@ -5038,7 +5050,7 @@
 
 /// An expression representing a reference to a function, possibly with type
 /// arguments applied to it, e.g. the expression `print` in `var x = print;`.
-class FunctionReferenceImpl extends ExpressionImpl
+class FunctionReferenceImpl extends CommentReferableExpressionImpl
     implements FunctionReference {
   ExpressionImpl _function;
 
@@ -5573,7 +5585,8 @@
 ///    identifier ::=
 ///        [SimpleIdentifier]
 ///      | [PrefixedIdentifier]
-abstract class IdentifierImpl extends ExpressionImpl implements Identifier {
+abstract class IdentifierImpl extends CommentReferableExpressionImpl
+    implements Identifier {
   @override
   bool get isAssignable => true;
 }
@@ -8449,7 +8462,7 @@
 ///
 ///    propertyAccess ::=
 ///        [Expression] '.' [SimpleIdentifier]
-class PropertyAccessImpl extends ExpressionImpl
+class PropertyAccessImpl extends CommentReferableExpressionImpl
     with NullShortableExpressionImpl
     implements PropertyAccess {
   /// The expression computing the object defining the property being accessed.
@@ -10353,7 +10366,8 @@
 /// The `.staticType` getter returns the type of the expression (which will
 /// always be the type `Type`).  To see the type represented by the type literal
 /// use `.typeName.type`.
-class TypeLiteralImpl extends ExpressionImpl implements TypeLiteral {
+class TypeLiteralImpl extends CommentReferableExpressionImpl
+    implements TypeLiteral {
   NamedTypeImpl _typeName;
 
   TypeLiteralImpl(this._typeName) {
diff --git a/pkg/analyzer/lib/src/dart/ast/ast_factory.dart b/pkg/analyzer/lib/src/dart/ast/ast_factory.dart
index f9e04f4..23b899cdf 100644
--- a/pkg/analyzer/lib/src/dart/ast/ast_factory.dart
+++ b/pkg/analyzer/lib/src/dart/ast/ast_factory.dart
@@ -206,8 +206,9 @@
 
   @override
   CommentReferenceImpl commentReference(
-          Token? newKeyword, Identifier identifier) =>
-      CommentReferenceImpl(newKeyword, identifier as IdentifierImpl);
+          Token? newKeyword, CommentReferableExpression expression) =>
+      CommentReferenceImpl(
+          newKeyword, expression as CommentReferableExpressionImpl);
 
   @override
   CompilationUnitImpl compilationUnit(
diff --git a/pkg/analyzer/lib/src/dart/ast/utilities.dart b/pkg/analyzer/lib/src/dart/ast/utilities.dart
index ec080e8..1b2249a 100644
--- a/pkg/analyzer/lib/src/dart/ast/utilities.dart
+++ b/pkg/analyzer/lib/src/dart/ast/utilities.dart
@@ -272,7 +272,7 @@
   bool visitCommentReference(CommentReference node) {
     CommentReference other = _other as CommentReference;
     return isEqualTokens(node.newKeyword, other.newKeyword) &&
-        isEqualNodes(node.identifier, other.identifier);
+        isEqualNodes(node.expression, other.expression);
   }
 
   @override
@@ -1796,8 +1796,8 @@
 
   @override
   bool visitCommentReference(covariant CommentReferenceImpl node) {
-    if (identical(node.identifier, _oldNode)) {
-      node.identifier = _newNode as Identifier;
+    if (identical(node.expression, _oldNode)) {
+      node.expression = _newNode as Identifier;
       return true;
     }
     return visitNode(node);
diff --git a/pkg/analyzer/lib/src/generated/element_resolver.dart b/pkg/analyzer/lib/src/generated/element_resolver.dart
index af56535..717940b 100644
--- a/pkg/analyzer/lib/src/generated/element_resolver.dart
+++ b/pkg/analyzer/lib/src/generated/element_resolver.dart
@@ -125,31 +125,31 @@
 
   @override
   void visitCommentReference(covariant CommentReferenceImpl node) {
-    var identifier = node.identifier;
-    if (identifier is SimpleIdentifierImpl) {
-      var element = _resolveSimpleIdentifier(identifier);
+    var expression = node.expression;
+    if (expression is SimpleIdentifierImpl) {
+      var element = _resolveSimpleIdentifier(expression);
       if (element == null) {
         return;
       }
-      identifier.staticElement = element;
+      expression.staticElement = element;
       if (node.newKeyword != null) {
         if (element is ClassElement) {
           var constructor = element.unnamedConstructor;
           if (constructor == null) {
             // TODO(brianwilkerson) Report this error.
           } else {
-            identifier.staticElement = constructor;
+            expression.staticElement = constructor;
           }
         } else {
           // TODO(brianwilkerson) Report this error.
         }
       }
-    } else if (identifier is PrefixedIdentifierImpl) {
-      var prefix = identifier.prefix;
+    } else if (expression is PrefixedIdentifierImpl) {
+      var prefix = expression.prefix;
       var prefixElement = _resolveSimpleIdentifier(prefix);
       prefix.staticElement = prefixElement;
 
-      var name = identifier.identifier;
+      var name = expression.identifier;
 
       if (prefixElement == null) {
         return;
diff --git a/pkg/analyzer/test/generated/new_as_identifier_parser_test.dart b/pkg/analyzer/test/generated/new_as_identifier_parser_test.dart
index 7fbe061..bd35b65 100644
--- a/pkg/analyzer/test/generated/new_as_identifier_parser_test.dart
+++ b/pkg/analyzer/test/generated/new_as_identifier_parser_test.dart
@@ -259,7 +259,7 @@
   void test_constructor_tearoff_in_comment_reference() {
     createParser('');
     var commentReference = parseCommentReference('C.new', 5)!;
-    var identifier = commentReference.identifier as PrefixedIdentifier;
+    var identifier = commentReference.expression as PrefixedIdentifier;
     expect(identifier.prefix.name, 'C');
     expect(identifier.identifier.name, 'new');
   }
diff --git a/pkg/analyzer/test/generated/simple_parser_test.dart b/pkg/analyzer/test/generated/simple_parser_test.dart
index f96e112..e183e2a 100644
--- a/pkg/analyzer/test/generated/simple_parser_test.dart
+++ b/pkg/analyzer/test/generated/simple_parser_test.dart
@@ -574,8 +574,8 @@
     var reference = parseCommentReference('new a.b', 7)!;
     expectNotNullIfNoErrors(reference);
     assertNoErrors();
-    expect(reference.identifier, isPrefixedIdentifier);
-    var prefixedIdentifier = reference.identifier as PrefixedIdentifier;
+    expect(reference.expression, isPrefixedIdentifier);
+    var prefixedIdentifier = reference.expression as PrefixedIdentifier;
     SimpleIdentifier prefix = prefixedIdentifier.prefix;
     expect(prefix.token, isNotNull);
     expect(prefix.name, "a");
@@ -592,8 +592,8 @@
     var reference = parseCommentReference('new a', 5)!;
     expectNotNullIfNoErrors(reference);
     assertNoErrors();
-    expect(reference.identifier, isSimpleIdentifier);
-    var identifier = reference.identifier as SimpleIdentifier;
+    expect(reference.expression, isSimpleIdentifier);
+    var identifier = reference.expression as SimpleIdentifier;
     expect(identifier.token, isNotNull);
     expect(identifier.name, "a");
     expect(identifier.offset, 9);
@@ -604,8 +604,8 @@
     var reference = parseCommentReference('operator ==', 5)!;
     expectNotNullIfNoErrors(reference);
     assertNoErrors();
-    expect(reference.identifier, isSimpleIdentifier);
-    var identifier = reference.identifier as SimpleIdentifier;
+    expect(reference.expression, isSimpleIdentifier);
+    var identifier = reference.expression as SimpleIdentifier;
     expect(identifier.token, isNotNull);
     expect(identifier.name, "==");
     expect(identifier.offset, 14);
@@ -616,8 +616,8 @@
     var reference = parseCommentReference('Object.operator==', 7)!;
     expectNotNullIfNoErrors(reference);
     assertNoErrors();
-    expect(reference.identifier, isPrefixedIdentifier);
-    var prefixedIdentifier = reference.identifier as PrefixedIdentifier;
+    expect(reference.expression, isPrefixedIdentifier);
+    var prefixedIdentifier = reference.expression as PrefixedIdentifier;
     SimpleIdentifier prefix = prefixedIdentifier.prefix;
     expect(prefix.token, isNotNull);
     expect(prefix.name, "Object");
@@ -634,8 +634,8 @@
     var reference = parseCommentReference('==', 5)!;
     expectNotNullIfNoErrors(reference);
     assertNoErrors();
-    expect(reference.identifier, isSimpleIdentifier);
-    var identifier = reference.identifier as SimpleIdentifier;
+    expect(reference.expression, isSimpleIdentifier);
+    var identifier = reference.expression as SimpleIdentifier;
     expect(identifier.token, isNotNull);
     expect(identifier.name, "==");
     expect(identifier.offset, 5);
@@ -646,8 +646,8 @@
     var reference = parseCommentReference('Object.==', 7)!;
     expectNotNullIfNoErrors(reference);
     assertNoErrors();
-    expect(reference.identifier, isPrefixedIdentifier);
-    var prefixedIdentifier = reference.identifier as PrefixedIdentifier;
+    expect(reference.expression, isPrefixedIdentifier);
+    var prefixedIdentifier = reference.expression as PrefixedIdentifier;
     SimpleIdentifier prefix = prefixedIdentifier.prefix;
     expect(prefix.token, isNotNull);
     expect(prefix.name, "Object");
@@ -664,8 +664,8 @@
     var reference = parseCommentReference('a.b', 7)!;
     expectNotNullIfNoErrors(reference);
     assertNoErrors();
-    expect(reference.identifier, isPrefixedIdentifier);
-    var prefixedIdentifier = reference.identifier as PrefixedIdentifier;
+    expect(reference.expression, isPrefixedIdentifier);
+    var prefixedIdentifier = reference.expression as PrefixedIdentifier;
     SimpleIdentifier prefix = prefixedIdentifier.prefix;
     expect(prefix.token, isNotNull);
     expect(prefix.name, "a");
@@ -682,8 +682,8 @@
     var reference = parseCommentReference('a', 5)!;
     expectNotNullIfNoErrors(reference);
     assertNoErrors();
-    expect(reference.identifier, isSimpleIdentifier);
-    var identifier = reference.identifier as SimpleIdentifier;
+    expect(reference.expression, isSimpleIdentifier);
+    var identifier = reference.expression as SimpleIdentifier;
     expect(identifier.token, isNotNull);
     expect(identifier.name, "a");
     expect(identifier.offset, 5);
@@ -694,8 +694,8 @@
     var reference = parseCommentReference('', 5)!;
     expectNotNullIfNoErrors(reference);
     assertNoErrors();
-    expect(reference.identifier, isSimpleIdentifier);
-    var identifier = reference.identifier as SimpleIdentifier;
+    expect(reference.expression, isSimpleIdentifier);
+    var identifier = reference.expression as SimpleIdentifier;
     expect(identifier, isNotNull);
     expect(identifier.isSynthetic, isTrue);
     expect(identifier.token, isNotNull);
@@ -715,7 +715,7 @@
     var reference = parseCommentReference('this', 5)!;
     expectNotNullIfNoErrors(reference);
     assertNoErrors();
-    var identifier = reference.identifier as SimpleIdentifier;
+    var identifier = reference.expression as SimpleIdentifier;
     expect(identifier.token, isNotNull);
     expect(identifier.name, "a");
     expect(identifier.offset, 5);
@@ -731,7 +731,7 @@
     expect(references, hasLength(1));
     CommentReference reference = references[0];
     expect(reference, isNotNull);
-    expect(reference.identifier, isNotNull);
+    expect(reference.expression, isNotNull);
     expect(reference.offset, 5);
   }
 
@@ -750,7 +750,8 @@
 
     expectReference(int index, String expectedText, int expectedOffset) {
       CommentReference reference = references[index];
-      expect(reference.identifier.name, expectedText);
+      var identifier = reference.expression as Identifier;
+      expect(identifier.name, expectedText);
       expect(reference.offset, expectedOffset);
     }
 
@@ -780,7 +781,8 @@
 
     expectReference(int index, String expectedText, int expectedOffset) {
       CommentReference reference = references[index];
-      expect(reference.identifier.name, expectedText);
+      var identifier = reference.expression as Identifier;
+      expect(identifier.name, expectedText);
       expect(reference.offset, expectedOffset);
     }
 
@@ -802,18 +804,18 @@
     {
       CommentReference reference = references[0];
       expect(reference, isNotNull);
-      expect(reference.identifier, isNotNull);
+      expect(reference.expression, isNotNull);
       expect(reference.offset, 12);
-      Token referenceToken = reference.identifier.beginToken;
+      Token referenceToken = reference.expression.beginToken;
       expect(referenceToken.offset, 12);
       expect(referenceToken.lexeme, 'a');
     }
     {
       CommentReference reference = references[1];
       expect(reference, isNotNull);
-      expect(reference.identifier, isNotNull);
+      expect(reference.expression, isNotNull);
       expect(reference.offset, 20);
-      Token referenceToken = reference.identifier.beginToken;
+      Token referenceToken = reference.expression.beginToken;
       expect(referenceToken.offset, 20);
       expect(referenceToken.lexeme, 'bb');
     }
@@ -829,11 +831,12 @@
     assertNoErrors();
     expect(references, hasLength(1));
     CommentReference reference = references[0];
-    Token referenceToken = reference.identifier.beginToken;
+    Token referenceToken = reference.expression.beginToken;
     expect(reference, isNotNull);
-    expect(reference.identifier, isNotNull);
-    expect(reference.identifier.isSynthetic, isTrue);
-    expect(reference.identifier.name, "");
+    expect(reference.expression, isNotNull);
+    var identifier = reference.expression as Identifier;
+    expect(identifier.isSynthetic, isTrue);
+    expect(identifier.name, "");
     // Should end with EOF token.
     Token nextToken = referenceToken.next!;
     expect(nextToken, isNotNull);
@@ -850,12 +853,13 @@
     assertNoErrors();
     expect(references, hasLength(1));
     CommentReference reference = references[0];
-    Token referenceToken = reference.identifier.beginToken;
+    Token referenceToken = reference.expression.beginToken;
     expect(reference, isNotNull);
     expect(referenceToken, same(reference.beginToken));
-    expect(reference.identifier, isNotNull);
-    expect(reference.identifier.isSynthetic, isFalse);
-    expect(reference.identifier.name, "namePrefix");
+    expect(reference.expression, isNotNull);
+    var identifier = reference.expression as Identifier;
+    expect(identifier.isSynthetic, isFalse);
+    expect(identifier.name, "namePrefix");
     // Should end with EOF token.
     Token nextToken = referenceToken.next!;
     expect(nextToken, isNotNull);
@@ -875,15 +879,15 @@
     expect(references, hasLength(3));
     CommentReference reference = references[0];
     expect(reference, isNotNull);
-    expect(reference.identifier, isNotNull);
+    expect(reference.expression, isNotNull);
     expect(reference.offset, 12);
     reference = references[1];
     expect(reference, isNotNull);
-    expect(reference.identifier, isNotNull);
+    expect(reference.expression, isNotNull);
     expect(reference.offset, 20);
     reference = references[2];
     expect(reference, isNotNull);
-    expect(reference.identifier, isNotNull);
+    expect(reference.expression, isNotNull);
     expect(reference.offset, 35);
   }
 
@@ -925,7 +929,7 @@
     expect(references, hasLength(1));
     CommentReference reference = references[0];
     expect(reference, isNotNull);
-    expect(reference.identifier, isNotNull);
+    expect(reference.expression, isNotNull);
     expect(reference.offset, 24);
   }
 
@@ -941,7 +945,7 @@
     expect(references, hasLength(1));
     CommentReference reference = references[0];
     expect(reference, isNotNull);
-    expect(reference.identifier, isNotNull);
+    expect(reference.expression, isNotNull);
     expect(reference.offset, 16);
   }
 
@@ -1011,7 +1015,7 @@
     expect(references, hasLength(1));
     CommentReference reference = references[0];
     expect(reference, isNotNull);
-    expect(reference.identifier, isNotNull);
+    expect(reference.expression, isNotNull);
     expect(reference.offset, 27);
   }
 
@@ -1035,7 +1039,7 @@
     expect(references, hasLength(1));
     CommentReference reference = references[0];
     expect(reference, isNotNull);
-    expect(reference.identifier, isNotNull);
+    expect(reference.expression, isNotNull);
     expect(reference.offset, 74);
   }
 
@@ -1051,7 +1055,7 @@
     expect(references, hasLength(1));
     CommentReference reference = references[0];
     expect(reference, isNotNull);
-    expect(reference.identifier, isNotNull);
+    expect(reference.expression, isNotNull);
     expect(reference.offset, 35);
   }
 
@@ -1075,7 +1079,7 @@
     expect(references, hasLength(1));
     CommentReference reference = references[0];
     expect(reference, isNotNull);
-    expect(reference.identifier, isNotNull);
+    expect(reference.expression, isNotNull);
     expect(reference.offset, 54);
   }
 
@@ -1091,7 +1095,7 @@
     expect(references, hasLength(1));
     CommentReference reference = references[0];
     expect(reference, isNotNull);
-    expect(reference.identifier, isNotNull);
+    expect(reference.expression, isNotNull);
     expect(reference.offset, 15);
   }
 
@@ -1107,7 +1111,7 @@
     expect(references, hasLength(1));
     CommentReference reference = references[0];
     expect(reference, isNotNull);
-    expect(reference.identifier, isNotNull);
+    expect(reference.expression, isNotNull);
     expect(reference.offset, 44);
   }
 
diff --git a/pkg/analyzer/test/generated/utilities_test.dart b/pkg/analyzer/test/generated/utilities_test.dart
index 0cbba91c..95aa605 100644
--- a/pkg/analyzer/test/generated/utilities_test.dart
+++ b/pkg/analyzer/test/generated/utilities_test.dart
@@ -294,9 +294,10 @@
 }
 
 class Getter_NodeReplacerTest_test_commentReference
-    implements NodeReplacerTest_Getter<CommentReference, Identifier> {
+    implements
+        NodeReplacerTest_Getter<CommentReference, CommentReferableExpression> {
   @override
-  Identifier get(CommentReference node) => node.identifier;
+  CommentReferableExpression get(CommentReference node) => node.expression;
 }
 
 class Getter_NodeReplacerTest_test_compilationUnit
diff --git a/pkg/analyzer/test/src/dart/resolution/mixin_test.dart b/pkg/analyzer/test/src/dart/resolution/mixin_test.dart
index 93fa507..fb6d6b1f 100644
--- a/pkg/analyzer/test/src/dart/resolution/mixin_test.dart
+++ b/pkg/analyzer/test/src/dart/resolution/mixin_test.dart
@@ -120,7 +120,7 @@
 mixin M {}
 ''');
 
-    var aRef = findNode.commentReference('a]').identifier;
+    var aRef = findNode.commentReference('a]').expression;
     assertElement(aRef, findElement.topGet('a'));
     assertTypeNull(aRef);
   }