Пример #1
0
        /// <summary>
        /// Gets the invoke method for a delegate type.
        /// </summary>
        /// <remarks>
        /// Returns null if the type is not a delegate type; or if the invoke method could not be found.
        /// </remarks>
        public static IMethod GetDelegateInvokeMethod(this IType type)
        {
            if (type == null)
            {
                throw new ArgumentNullException("type");
            }
            ITypeDefinition def = type.GetDefinition();

            if (def != null && def.ClassType == ClassType.Delegate)
            {
                foreach (IMethod method in def.Methods)
                {
                    if (method.Name == "Invoke")
                    {
                        ParameterizedType pt = type as ParameterizedType;
                        if (pt != null)
                        {
                            SpecializedMethod m = new SpecializedMethod(method);
                            m.SetDeclaringType(pt);
                            var substitution = pt.GetSubstitution();
                            m.SubstituteTypes(t => new SubstitutionTypeReference(t, substitution));
                            return(m);
                        }
                        return(method);
                    }
                }
            }
            return(null);
        }
Пример #2
0
        public void GetIndexDoubleSpecialization()
        {
            var testClass = GetTypeDefinition(typeof(GenericClass <,>));
            // GenericClass<A, B>.GetIndex<T>
            var methodDef = testClass.Methods.Single(me => me.Name == "GetIndex");

            // GenericClass<B, A>.GetIndex<A>
            var m1 = new SpecializedMethod(methodDef, new TypeParameterSubstitution(
                                               new[] { testClass.TypeParameters[1], testClass.TypeParameters[0] },
                                               new[] { testClass.TypeParameters[0] }
                                               ));
            // GenericClass<string, int>.GetIndex<int>
            var m2 = new SpecializedMethod(m1, new TypeParameterSubstitution(
                                               new[] { compilation.FindType(KnownTypeCode.Int32), compilation.FindType(KnownTypeCode.String) },
                                               null
                                               ));

            // GenericClass<string, int>.GetIndex<int>
            var m12 = new SpecializedMethod(methodDef, new TypeParameterSubstitution(
                                                new[] { compilation.FindType(KnownTypeCode.String), compilation.FindType(KnownTypeCode.Int32) },
                                                new[] { compilation.FindType(KnownTypeCode.Int32) }
                                                ));

            Assert.AreEqual(m12, m2);
        }
Пример #3
0
        public IParameterizedMember GetBestCandidateWithSubstitutedTypeArguments()
        {
            if (bestCandidate == null)
            {
                return(null);
            }
            IMethod method = bestCandidate.Member as IMethod;

            if (method != null && method.TypeParameters.Count > 0)
            {
                SpecializedMethod sm = method as SpecializedMethod;
                if (sm != null)
                {
                    // Do not compose the substitutions, but merge them.
                    // This is required for InvocationTests.SubstituteClassAndMethodTypeParametersAtOnce
                    return(new SpecializedMethod(
                               (IMethod)method.MemberDefinition,
                               new TypeParameterSubstitution(sm.Substitution.ClassTypeArguments, bestCandidate.InferredTypes)));
                }
                else
                {
                    return(new SpecializedMethod(method, new TypeParameterSubstitution(null, bestCandidate.InferredTypes)));
                }
            }
            else
            {
                return(bestCandidate.Member);
            }
        }
Пример #4
0
        public static IMethod CreateTypeCheckMethod(IType type, ICompilation compilation)
        {
            IMethod method = new DefaultResolvedMethod(new DefaultUnresolvedMethod(type.GetDefinition().Parts[0], "IsInstanceOfType"), compilation.TypeResolveContext.WithCurrentTypeDefinition(type.GetDefinition()));

            if (type is ParameterizedType)
            {
                method = new SpecializedMethod(method, new TypeParameterSubstitution(classTypeArguments: ((ParameterizedType)type).TypeArguments, methodTypeArguments: null));
            }
            return(method);
        }
Пример #5
0
        public IEnumerable <IMethod> GetConstructors(ITypeResolveContext context, Predicate <IMethod> filter = null)
        {
            Substitution   substitution = new Substitution(typeArguments);
            List <IMethod> methods      = genericType.GetConstructors(context, filter).ToList();

            for (int i = 0; i < methods.Count; i++)
            {
                SpecializedMethod m = new SpecializedMethod(methods[i]);
                m.SetDeclaringType(this);
                m.SubstituteTypes(context, substitution);
                methods[i] = m;
            }
            return(methods);
        }
Пример #6
0
        TypeParameterSubstitution GetSubstitution(Candidate candidate)
        {
            SpecializedMethod sm = candidate.Member as SpecializedMethod;

            if (sm != null)
            {
                // Do not compose the substitutions, but merge them.
                // This is required for InvocationTests.SubstituteClassAndMethodTypeParametersAtOnce
                return(new TypeParameterSubstitution(sm.Substitution.ClassTypeArguments, candidate.InferredTypes));
            }
            else
            {
                return(new TypeParameterSubstitution(null, candidate.InferredTypes));
            }
        }
Пример #7
0
        public static IMethod CreateDummyMethodForFieldInitialization(IMember member, ICompilation compilation)
        {
            var unresolved = new DefaultUnresolvedMethod(member.DeclaringTypeDefinition.Parts[0], "initialization for " + member.Name)
            {
                Parameters = { new DefaultUnresolvedParameter(member.ReturnType.ToTypeReference(), "value") },
                IsStatic   = member.IsStatic,
            };
            IMethod method = new DefaultResolvedMethod(unresolved, compilation.TypeResolveContext.WithCurrentTypeDefinition(member.DeclaringTypeDefinition));

            if (member.DeclaringType is ParameterizedType)
            {
                method = new SpecializedMethod(method, new TypeParameterSubstitution(classTypeArguments: ((ParameterizedType)member.DeclaringType).TypeArguments, methodTypeArguments: null));
            }
            return(method);
        }
Пример #8
0
        public IEnumerable <IMethod> GetMethods(ITypeResolveContext context, Predicate <IMethod> filter = null)
        {
            Substitution substitution = new Substitution(typeArguments);
            Func <ITypeReference, ITypeReference> substitutionFunc = t => t.Resolve(context).AcceptVisitor(substitution);
            List <IMethod> methods = genericType.GetMethods(context, filter).ToList();

            for (int i = 0; i < methods.Count; i++)
            {
                SpecializedMethod m = new SpecializedMethod(methods[i]);
                m.SetDeclaringType(this);
                m.SubstituteTypes(substitutionFunc);
                methods[i] = m;
            }
            return(methods);
        }
Пример #9
0
        public void GetIndexSpecializedTypeParameter()
        {
            var testClass = GetTypeDefinition(typeof(GenericClass <,>));
            var methodDef = testClass.Methods.Single(me => me.Name == "GetIndex");
            var m         = new SpecializedMethod(methodDef, new TypeParameterSubstitution(
                                                      new[] { compilation.FindType(KnownTypeCode.Int16), compilation.FindType(KnownTypeCode.Int32) },
                                                      null
                                                      ));

            Assert.AreEqual("T", m.TypeParameters[0].Name);
            Assert.AreEqual(EntityType.Method, m.TypeParameters[0].OwnerType);
            Assert.AreSame(m, m.TypeParameters[0].Owner);

            ParameterizedType constraint = (ParameterizedType)m.TypeParameters[0].DirectBaseTypes.First();

            Assert.AreEqual("IEquatable", constraint.Name);
            Assert.AreEqual(1, constraint.TypeParameterCount);
            Assert.AreEqual(1, constraint.TypeArguments.Count);
            Assert.AreSame(m.TypeParameters[0], constraint.TypeArguments[0]);
        }
Пример #10
0
        public void ConvertAllInGenericMethod()
        {
            string program = @"using System;
class TestClass {
	static void Method<T>(System.Collections.Generic.List<T> list) {
		$list.ConvertAll(x => (int)x)$;
	}
}";
            var    rr      = Resolve <CSharpInvocationResolveResult>(program);

            Assert.IsFalse(rr.IsError);
            SpecializedMethod m = (SpecializedMethod)rr.Member;

            Assert.AreEqual("System.Int32", m.TypeArguments[0].ReflectionName);
            Assert.AreEqual("System.Converter`2[[``0],[System.Int32]]", m.Parameters[0].Type.ReflectionName);

            var crr = (ConversionResolveResult)rr.Arguments[0];

            Assert.IsTrue(crr.Conversion.IsAnonymousFunctionConversion);
            Assert.AreEqual("System.Converter`2[[``0],[System.Int32]]", crr.Type.ReflectionName);
        }
Пример #11
0
        IMember Specialize(IMember member, Func <ITypeReference, ITypeReference> substitution)
        {
            IMethod method = member as IMethod;

            if (method != null)
            {
                SpecializedMethod m = new SpecializedMethod(method);
                m.SetDeclaringType(this);
                m.SubstituteTypes(substitution);
                return(m);
            }
            IProperty property = member as IProperty;

            if (property != null)
            {
                SpecializedProperty p = new SpecializedProperty(property);
                p.SetDeclaringType(this);
                p.SubstituteTypes(substitution);
                return(p);
            }
            IField field = member as IField;

            if (field != null)
            {
                SpecializedField f = new SpecializedField(field);
                f.SetDeclaringType(this);
                f.ReturnType = substitution(f.ReturnType);
                return(f);
            }
            IEvent ev = member as IEvent;

            if (ev != null)
            {
                SpecializedEvent e = new SpecializedEvent(ev);
                e.SetDeclaringType(this);
                e.ReturnType = substitution(e.ReturnType);
                return(e);
            }
            throw new ArgumentException("Unknown member");
        }
Пример #12
0
 public IMethod Specialize(TypeParameterSubstitution substitution) => SpecializedMethod.Create(this, substitution);