diff --git a/src/Compilers/CSharp/Portable/SymbolDisplay/SymbolDisplayVisitor_Minimal.cs b/src/Compilers/CSharp/Portable/SymbolDisplay/SymbolDisplayVisitor_Minimal.cs index b7a82cb78d6b0..6f1c92c44ad83 100644 --- a/src/Compilers/CSharp/Portable/SymbolDisplay/SymbolDisplayVisitor_Minimal.cs +++ b/src/Compilers/CSharp/Portable/SymbolDisplay/SymbolDisplayVisitor_Minimal.cs @@ -195,27 +195,41 @@ private IDictionary CreateAliasMap() // NOTE(cyrusn): If we're currently in a block of usings, then we want to collect the // aliases that are higher up than this block. Using aliases declared in a block of - // usings are not usable from within that same block. - var usingDirective = GetAncestorOrThis(startNode); - if (usingDirective != null) + // usings are not usable from within that same block. This loop moves us outside of the + // immediately enclosing using directive, if any. + while (startNode != null) { - startNode = usingDirective.Parent!.Parent!; + if (startNode is UsingDirectiveSyntax) + { + startNode = startNode.Parent!.Parent!; + break; + } + + startNode = startNode.Parent; } - var usingAliases = GetAncestorsOrThis(startNode) - .SelectMany(n => n.Usings) - .Concat(GetAncestorsOrThis(startNode).SelectMany(c => c.Usings)) - .Where(u => u.Alias != null) - .Select(u => semanticModel.GetDeclaredSymbol(u) as IAliasSymbol) - .WhereNotNull(); + startNode ??= token.Parent; var builder = ImmutableDictionary.CreateBuilder(); - foreach (var alias in usingAliases) + while (startNode != null) { - if (!builder.ContainsKey(alias.Target)) + var usings = (startNode as BaseNamespaceDeclarationSyntax)?.Usings; + usings ??= (startNode as CompilationUnitSyntax)?.Usings; + + if (usings != null) { - builder.Add(alias.Target, alias); + foreach (var u in usings) + { + if (u.Alias != null + && semanticModel.GetDeclaredSymbol(u) is IAliasSymbol aliasSymbol + && !builder.ContainsKey(aliasSymbol.Target)) + { + builder.Add(aliasSymbol.Target, aliasSymbol); + } + } } + + startNode = startNode.Parent; } return builder.ToImmutable(); @@ -287,18 +301,6 @@ private string RemoveAttributeSuffixIfNecessary(INamedTypeSymbol symbol, string return symbolName; } - private static T? GetAncestorOrThis(SyntaxNode node) where T : SyntaxNode - { - return GetAncestorsOrThis(node).FirstOrDefault(); - } - - private static IEnumerable GetAncestorsOrThis(SyntaxNode node) where T : SyntaxNode - { - return node == null - ? SpecializedCollections.EmptyEnumerable() - : node.AncestorsAndSelf().OfType(); - } - private IDictionary AliasMap { get