Ejemplo n.º 1
0
        IEnumerable <ISymbol> HandleCustomAttribute(ITypeDefinition attributeType, AnalyzerScope scope, CancellationToken ct)
        {
            var genericContext = new Decompiler.TypeSystem.GenericContext();             // type arguments do not matter for this analyzer.

            foreach (var module in scope.GetModulesInScope(ct))
            {
                var ts = scope.ConstructTypeSystem(module);
                ct.ThrowIfCancellationRequested();
                var decoder = new FindTypeDecoder(ts.MainModule, attributeType);

                var referencedParameters = new HashSet <ParameterHandle>();
                foreach (var h in module.Metadata.CustomAttributes)
                {
                    var customAttribute = module.Metadata.GetCustomAttribute(h);
                    if (IsCustomAttributeOfType(customAttribute.Constructor, module.Metadata, decoder))
                    {
                        if (customAttribute.Parent.Kind == HandleKind.Parameter)
                        {
                            referencedParameters.Add((ParameterHandle)customAttribute.Parent);
                        }
                        else
                        {
                            var parent = AnalyzerHelpers.GetParentEntity(ts, customAttribute);
                            if (parent != null)
                            {
                                yield return(parent);
                            }
                        }
                    }
                }
                if (referencedParameters.Count > 0)
                {
                    foreach (var h in module.Metadata.MethodDefinitions)
                    {
                        var md = module.Metadata.GetMethodDefinition(h);
                        foreach (var p in md.GetParameters())
                        {
                            if (referencedParameters.Contains(p))
                            {
                                var method = ts.MainModule.ResolveMethod(h, genericContext);
                                if (method != null)
                                {
                                    if (method.IsAccessor)
                                    {
                                        yield return(method.AccessorOwner);
                                    }
                                    else
                                    {
                                        yield return(method);
                                    }
                                }
                                break;
                            }
                        }
                    }
                }
            }
        }
        IEnumerable <ISymbol> HandleCustomAttribute(ITypeDefinition attributeType, AnalyzerScope scope)
        {
            var genericContext = new GenericContext();             // type arguments do not matter for this analyzer.

            foreach (var module in scope.GetAllModules())
            {
                var ts = new DecompilerTypeSystem(module, module.GetAssemblyResolver());
                var referencedParameters = new HashSet <ParameterHandle>();
                foreach (var h in module.Metadata.CustomAttributes)
                {
                    var customAttribute = module.Metadata.GetCustomAttribute(h);
                    var attributeCtor   = ts.MainModule.ResolveMethod(customAttribute.Constructor, genericContext);
                    if (attributeCtor.DeclaringTypeDefinition != null &&
                        attributeCtor.ParentModule.PEFile == attributeType.ParentModule.PEFile &&
                        attributeCtor.DeclaringTypeDefinition.MetadataToken == attributeType.MetadataToken)
                    {
                        if (customAttribute.Parent.Kind == HandleKind.Parameter)
                        {
                            referencedParameters.Add((ParameterHandle)customAttribute.Parent);
                        }
                        else
                        {
                            var parent = GetParentEntity(ts, customAttribute);
                            if (parent != null)
                            {
                                yield return(parent);
                            }
                        }
                    }
                }
                if (referencedParameters.Count > 0)
                {
                    foreach (var h in module.Metadata.MethodDefinitions)
                    {
                        var md = module.Metadata.GetMethodDefinition(h);
                        foreach (var p in md.GetParameters())
                        {
                            if (referencedParameters.Contains(p))
                            {
                                var method = ts.MainModule.ResolveMethod(h, genericContext);
                                if (method != null)
                                {
                                    if (method.IsAccessor)
                                    {
                                        yield return(method.AccessorOwner);
                                    }
                                    else
                                    {
                                        yield return(method);
                                    }
                                }
                                break;
                            }
                        }
                    }
                }
            }
        }
        IEnumerable <IEnumerable <ISymbol> > HandleBuiltinAttribute(KnownAttribute attribute, AnalyzerScope scope)
        {
            IEnumerable <ISymbol> ScanTypes(DecompilerTypeSystem ts)
            {
                return(ts.MainModule.TypeDefinitions
                       .Where(t => t.HasAttribute(attribute)));
            }

            IEnumerable <ISymbol> ScanMethods(DecompilerTypeSystem ts)
            {
                return(ts.MainModule.TypeDefinitions
                       .SelectMany(t => t.Members.OfType <IMethod>())
                       .Where(m => m.HasAttribute(attribute))
                       .Select(m => m.AccessorOwner ?? m));
            }

            IEnumerable <ISymbol> ScanFields(DecompilerTypeSystem ts)
            {
                return(ts.MainModule.TypeDefinitions
                       .SelectMany(t => t.Fields)
                       .Where(f => f.HasAttribute(attribute)));
            }

            IEnumerable <ISymbol> ScanProperties(DecompilerTypeSystem ts)
            {
                return(ts.MainModule.TypeDefinitions
                       .SelectMany(t => t.Properties)
                       .Where(p => p.HasAttribute(attribute)));
            }

            IEnumerable <ISymbol> ScanParameters(DecompilerTypeSystem ts)
            {
                return(ts.MainModule.TypeDefinitions
                       .SelectMany(t => t.Members.OfType <IMethod>())
                       .Where(m => m.Parameters.Any(p => p.HasAttribute(attribute)))
                       .Select(m => m.AccessorOwner ?? m));
            }

            foreach (Decompiler.Metadata.PEFile module in scope.GetAllModules())
            {
                var ts = new DecompilerTypeSystem(module, module.GetAssemblyResolver());

                switch (attribute)
                {
                case KnownAttribute.Serializable:
                case KnownAttribute.ComImport:
                case KnownAttribute.StructLayout:
                    yield return(ScanTypes(ts));

                    break;

                case KnownAttribute.DllImport:
                case KnownAttribute.PreserveSig:
                case KnownAttribute.MethodImpl:
                    yield return(ScanMethods(ts));

                    break;

                case KnownAttribute.FieldOffset:
                case KnownAttribute.NonSerialized:
                    yield return(ScanFields(ts));

                    break;

                case KnownAttribute.MarshalAs:
                    yield return(ScanFields(ts));

                    yield return(ScanParameters(ts));

                    goto case KnownAttribute.Out;

                case KnownAttribute.Optional:
                case KnownAttribute.In:
                case KnownAttribute.Out:
                    yield return(ScanParameters(ts));

                    break;

                case KnownAttribute.IndexerName:
                    yield return(ScanProperties(ts));

                    break;
                }
            }
        }
Ejemplo n.º 4
0
        static IEnumerable <ISymbol> AnalyzeModule(ITypeDefinition analyzedType, AnalyzerScope scope, PEFile module)
        {
            var metadata   = module.Metadata;
            var typeSystem = scope.ConstructTypeSystem(module);
            var decoder    = new FindTypeDecoder(typeSystem.MainModule, analyzedType);

            //// resolve type refs
            //int rowCount = metadata.GetTableRowCount(TableIndex.TypeRef);
            //BitSet typeReferences = new BitSet(rowCount);
            //for (int row = 0; row < rowCount; row++)
            //{
            //	var h = MetadataTokens.TypeReferenceHandle(row + 1);
            //	typeReferences[row] = decoder.GetTypeFromReference(metadata, h, 0);
            //}

            //// resolve type specs
            //rowCount = metadata.GetTableRowCount(TableIndex.TypeSpec);
            //BitSet typeSpecifications = new BitSet(rowCount);
            //for (int row = 0; row < rowCount; row++)
            //{
            //	var h = MetadataTokens.TypeSpecificationHandle(row + 1);
            //	typeSpecifications[row] = decoder.GetTypeFromSpecification(metadata, default, h, 0);
            //}

            foreach (ISymbol result in FindUsesInAttributes(typeSystem, metadata, decoder, analyzedType))
            {
                yield return(result);
            }

            foreach (var h in metadata.TypeDefinitions)
            {
                var  td    = metadata.GetTypeDefinition(h);
                bool found = decoder.GetTypeFromEntity(metadata, td.GetBaseTypeOrNil());
                foreach (var ih in td.GetInterfaceImplementations())
                {
                    var ii = metadata.GetInterfaceImplementation(ih);
                    found |= decoder.GetTypeFromEntity(metadata, ii.Interface);
                }

                found |= FindUsesInGenericConstraints(metadata, td.GetGenericParameters(), decoder);

                if (found)
                {
                    yield return(typeSystem.MainModule.GetDefinition(h));
                }
            }

            foreach (var h in metadata.MethodDefinitions)
            {
                var  md    = metadata.GetMethodDefinition(h);
                var  msig  = md.DecodeSignature(decoder, default);
                bool found = FindTypeDecoder.AnyInMethodSignature(msig);
                found |= FindUsesInGenericConstraints(metadata, md.GetGenericParameters(), decoder);
                if (found || ScanMethodBody(analyzedType, module, md, decoder))
                {
                    var method = typeSystem.MainModule.GetDefinition(h);
                    yield return(method?.AccessorOwner ?? method);
                }
            }

            foreach (var h in metadata.FieldDefinitions)
            {
                var fd = metadata.GetFieldDefinition(h);
                if (fd.DecodeSignature(decoder, default))
                {
                    yield return(typeSystem.MainModule.GetDefinition(h));
                }
            }

            foreach (var h in metadata.PropertyDefinitions)
            {
                var pd   = metadata.GetPropertyDefinition(h);
                var psig = pd.DecodeSignature(decoder, default);
                if (FindTypeDecoder.AnyInMethodSignature(psig))
                {
                    yield return(typeSystem.MainModule.GetDefinition(h));
                }
            }

            foreach (var h in metadata.EventDefinitions)
            {
                var ed = metadata.GetEventDefinition(h);
                if (decoder.GetTypeFromEntity(metadata, ed.Type))
                {
                    yield return(typeSystem.MainModule.GetDefinition(h));
                }
            }
        }