Ejemplo n.º 1
0
 public static bool IsAssignableTo(this ITypeSymbol type,
                                   INamedTypeSymbol symbol, SymbolEqualityComparer comparer = null)
 {
     comparer ??= SymbolEqualityComparer.Default;
     return(type.Equals(symbol, comparer) ||
            type.IsInheriting(symbol, comparer) ||
            type.IsImplementing(symbol, comparer));
 }
        //internal override NamedTypeSymbol FixedImplementationType(PEModuleBuilder emitModule)
        //{
        //    // This occurs rarely, if ever.  The scenario would be a generic struct
        //    // containing a fixed-size buffer.  Given the rarity there would be little
        //    // benefit to "optimizing" the performance of this by caching the
        //    // translated implementation type.
        //    return (NamedTypeSymbol)_containingType.TypeSubstitution.SubstituteType(_originalDefinition.FixedImplementationType(emitModule)).Type;
        //}

        public override bool Equals(ISymbol other, SymbolEqualityComparer equalityComparer)
        {
            if ((object)this == other)
            {
                return(true);
            }

            return(other is SubstitutedFieldSymbol f && _token == f._token && SymbolEqualityComparer.Default.Equals(_originalDefinition, f._originalDefinition));
        }
Ejemplo n.º 3
0
        public override sealed bool Equals(ISymbol obj, SymbolEqualityComparer equalityComparer)
        {
            var t2 = obj as TypeSymbol;

            if ((object)t2 == null)
            {
                return(false);
            }
            return(this.Equals(t2, false, false));
        }
Ejemplo n.º 4
0
        public bool Equals(MissingAssemblySymbol other, SymbolEqualityComparer _)
        {
            if (ReferenceEquals(other, null))
            {
                return(false);
            }

            if (ReferenceEquals(this, other))
            {
                return(true);
            }

            return(identity.Equals(other.Identity));
        }
        public sealed override bool Equals(ISymbol obj, SymbolEqualityComparer equalityComparer)
        {
            if ((object)this == obj)
            {
                return(true);
            }

            // Equality of ordinal and containing symbol is a correct
            // implementation for all ParameterSymbols, but we don't
            // define it on the base type because most can simply use
            // ReferenceEquals.

            return(obj is WrappedParameterSymbol other &&
                   this.Ordinal == other.Ordinal &&
                   SymbolEqualityComparer.Default.Equals(this.ContainingSymbol, other.ContainingSymbol));
        }
Ejemplo n.º 6
0
        private static bool IsInheriting(this ITypeSymbol type,
                                         INamedTypeSymbol symbol, SymbolEqualityComparer comparer = null)
        {
            comparer ??= SymbolEqualityComparer.Default;
            var baseType = type.BaseType;

            while (baseType != null)
            {
                if (symbol.Equals(baseType, comparer))
                {
                    return(true);
                }
                baseType = baseType.BaseType;
            }
            return(false);
        }
Ejemplo n.º 7
0
        public override bool Equals(ISymbol other, SymbolEqualityComparer equalityComparer)
        {
            if (ReferenceEquals(null, other))
            {
                return(false);
            }

            if (ReferenceEquals(this, other))
            {
                return(true);
            }

            // This checks if the property have the same definition and the type parameters on the containing types have been
            // substituted in the same way.
            return(other is PropertySymbol p && this.ContainingType == p.ContainingType && ReferenceEquals(this.OriginalDefinition, p.OriginalDefinition));
        }
Ejemplo n.º 8
0
 private static bool IsImplementing(this ITypeSymbol type,
                                    INamedTypeSymbol symbol, SymbolEqualityComparer comparer = null)
 {
     comparer ??= SymbolEqualityComparer.Default;
     foreach (var @interface in type.AllInterfaces)
     {
         if (@interface.Equals(symbol, comparer) ||
             @interface.OriginalDefinition.Equals(symbol, comparer))
         {
             return(true);
         }
         if (IsImplementing(@interface, symbol, comparer))
         {
             return(true);
         }
     }
     return(false);
 }
Ejemplo n.º 9
0
        internal static IEnumerable <INamedTypeSymbol> GetAOTGenerators(Compilation compilation)
        {
            INamedTypeSymbol egta = compilation.GetTypeByMetadataName(typeof(EmbedGeneratedTypeAttribute).FullName) !;

            #pragma warning disable RS1024 // Compare symbols correctly
            HashSet <INamedTypeSymbol> returnedGenerators = new(SymbolEqualityComparer);
            #pragma warning restore RS1024

            foreach (AttributeData attr in compilation.Assembly.GetAttributes())
            {
                if (SymbolEqualityComparer.Equals(attr.AttributeClass, egta))
                {
                    Debug.Assert(attr.ConstructorArguments.Length is 1);

                    INamedTypeSymbol generator = (INamedTypeSymbol)attr.ConstructorArguments[0].Value !;
                    if (returnedGenerators.Add(generator))
                    {
                        yield return(generator);
                    }
                }
            }
        }
Ejemplo n.º 10
0
 // By default, we do reference equality. This can be overridden.
 public virtual bool Equals(ISymbol other, SymbolEqualityComparer equalityComparer)
 {
     return((object)other == this);
 }
 public static bool SourceEquals(this ISymbol symbol, ISymbol target, SymbolEqualityComparer comparer) => symbol.OriginalDefinition.Equals(target.OriginalDefinition, comparer);
Ejemplo n.º 12
0
        private static void LAA1002_DictionarySetEnumeration(OperationAnalysisContext context)
        {
            const string           ns           = "System.Collections";
            SymbolDisplayFormat    symbolFormat = SymbolDisplayFormat.CSharpErrorMessageFormat;
            Compilation            comp         = context.Compilation;
            SymbolEqualityComparer comparer     = SymbolEqualityComparer.Default;

            bool TypeEquals(ITypeSymbol?valType, string metadataName) => valType is ITypeSymbol a &&
            comp.GetTypeByMetadataName(metadataName) is INamedTypeSymbol b &&
            comparer.Equals(a, b);

            string[] dictOrSets =
            {
                $"{ns}.Generic.IDictionary`2",
                $"{ns}.Generic.IReadOnlyDictionary`2",
                $"{ns}.Immutable.IImmutableDictionary`2",
                $"{ns}.IDictionary",
                $"{ns}.Generic.ISet`1",
                $"{ns}.Immutable.IImmutableSet`1",
            };

            string[] sortedTypes =
            {
                $"{ns}.Generic.SortedDictionary`2",
                $"{ns}.Immutable.ImmutableSortedDictionary`2",
                $"{ns}.Generic.SortedSet`1",
                $"{ns}.Immutable.ImmutableSortedSet`1",
                "Bencodex.Types.Dictionary",
            };

            bool IsDictOrSet(ITypeSymbol?valType) =>
            valType is ITypeSymbol t && t.OriginalDefinition.AllInterfaces
            .OfType <ITypeSymbol>()
            .Select(ifce => ifce.OriginalDefinition)
            .OfType <ITypeSymbol>()
            .Any(i => dictOrSets.Any(dst => TypeEquals(i, dst)));

            bool IsUnordered(ITypeSymbol?valType) =>
            valType is ITypeSymbol t && IsDictOrSet(t) &&
            !sortedTypes.Any(sortedType => TypeEquals(t.OriginalDefinition, sortedType));

            switch (context.Operation)
            {
            case IConversionOperation conv:
            {
                ITypeSymbol?endType = conv.Type;
                if (!TypeEquals(endType?.OriginalDefinition, $"{ns}.Generic.IEnumerable`1") &&
                    !TypeEquals(endType, $"{ns}.IEnumerable"))
                {
                    return;
                }

                if (conv.Parent is IArgumentOperation arg &&
                    arg.Parent is IInvocationOperation invoke &&
                    invoke.TargetMethod.IsGenericMethod &&
                    invoke.TargetMethod.OriginalDefinition is IMethodSymbol proto)
                {
                    var method = invoke.TargetMethod.Name;
                    if (method.StartsWith("OrderBy") &&
                        TypeEquals(proto.ContainingType, "System.Linq.Enumerable") &&
                        TypeEquals(
                            proto.ReturnType.OriginalDefinition,
                            "System.Linq.IOrderedEnumerable`1"
                            ))
                    {
                        // Ignores Linq's .OrderBy()/OrderByDescending() methods.
                        return;
                    }
                    else if (method.StartsWith("To") &&
                             (method.EndsWith("Dictionary") || method.EndsWith("Set")) &&
                             IsDictOrSet(proto.ReturnType))
                    {
                        // Ignores .ToDictionary()/ToHashSet() etc.
                        return;
                    }
                }

                if (conv.Parent is IArgumentOperation arg1 &&
                    arg1.Parent is IObjectCreationOperation @new &&
                    IsDictOrSet(@new.Type))
                {
                    // Ignores new Dictionary()/new HashSet() etc.
                    return;
                }

                ITypeSymbol?valType = conv.Operand?.Type;
                if (IsUnordered(valType))
                {
                    string func = "enumerating";
                    if (conv.Parent is IArgumentOperation argConv)
                    {
                        func = argConv.Parent switch
                        {
                            IObjectCreationOperation c =>
                            $"passing to {c.Constructor.ToDisplayString(symbolFormat)} " +
                            "constructor",
                            IInvocationOperation m =>
                            $"passing to {m.TargetMethod.ToDisplayString(symbolFormat)} " +
                            "method",
                                                     _ => func,
                        };
                    }

                    Diagnostic diag = Diagnostic.Create(
                        Rules[$"{IdPrefix}1002"],
                        conv.Syntax.GetLocation(),
                        valType !.ToDisplayString(symbolFormat),
                        func
                        );
                    context.ReportDiagnostic(diag);
                }

                break;
            }

            case IForEachLoopOperation loop:
            {
                IOperation  collection = loop.Collection;
                ITypeSymbol?collType   = collection.Type;
                if (IsUnordered(collType))
                {
                    Diagnostic diag = Diagnostic.Create(
                        Rules[$"{IdPrefix}1002"],
                        collection.Syntax.GetLocation(),
                        collType.ToDisplayString(symbolFormat),
                        "iterating via foreach"
                        );
                    context.ReportDiagnostic(diag);
                }

                break;
            }
            }
        }
        private static IRelatedSymbolProvider CreateRelatedSymbolProvider([NotNull] IRoslynWorkspaceProvider roslynWorkspaceProvider)
        {
            var symbolEqualityComparer = new SymbolEqualityComparer();

            return(new RelatedSymbolProvider(roslynWorkspaceProvider, symbolEqualityComparer));
        }
 public override bool Equals(ISymbol other, SymbolEqualityComparer equalityComparer)
 {
     return(other is MissingNamespaceSymbol missing && _name.Equals(missing._name) && SymbolEqualityComparer.Default.Equals(_containingSymbol, missing._containingSymbol));
 }
Ejemplo n.º 15
0
 public override bool Equals(ISymbol other, SymbolEqualityComparer equalityComparer)
 {
     return(other is MissingAssemblySymbol missing && Equals(missing, equalityComparer));
 }
Ejemplo n.º 16
0
 public bool Equals(ISymbol other, SymbolEqualityComparer equalityComparer)
 {
     return(this.Equals(other));
 }
Ejemplo n.º 17
0
 public bool Equals(ISymbol other, SymbolEqualityComparer equalityComparer)
 => throw new NotImplementedException();
Ejemplo n.º 18
0
 public bool Equals(ISymbol other, SymbolEqualityComparer equalityComparer)
 => Equals(other);
Ejemplo n.º 19
0
        public static bool IsAssignableTo(this SyntaxNode node,
                                          SemanticModel model, INamedTypeSymbol symbol, SymbolEqualityComparer comparer = null)
        {
            comparer ??= SymbolEqualityComparer.Default;
            var type = node.GetTypeSymbol(model);

            return(IsAssignableTo(type, symbol, comparer));
        }