public static TypeReference GetChildrenType(this ModuleDefinition module, TypeReference type) { if (type.IsArray) return type.GetElementType(); var getIEnumerableInterfaceChild = new Func<TypeReference, TypeReference>(typeReference => { if (typeReference.IsGenericInstance) { var genericType = typeReference as GenericInstanceType; if (genericType != null) { var genericInstances = genericType.GetGenericInstances(); // We have to make some exceptions to dictionaries var ienumerableInterface = genericInstances.FirstOrDefault(x => x.FullName.StartsWith("System.Collections.Generic.IDictionary`2<")); // If we have more than 1 generic argument then we try to get a IEnumerable<> // interface otherwise we just return the last argument in the list if (ienumerableInterface == null) ienumerableInterface = genericInstances.FirstOrDefault(x => x.FullName.StartsWith("System.Collections.Generic.IEnumerable`1<")); // We just don't know :( if (ienumerableInterface == null) return module.ImportReference(typeof(object)); return (ienumerableInterface as GenericInstanceType).GenericArguments[0]; } } return null; }); var result = getIEnumerableInterfaceChild(type); if (result != null) return result; // This might be a type that inherits from list<> or something... lets find out if (type.BetterResolve().GetInterfaces().Any(x => x.FullName == "System.Collections.Generic.IEnumerable`1")) { // if this is the case we will dig until we find a generic instance type var baseType = type.BetterResolve().BaseType; while (baseType != null) { result = getIEnumerableInterfaceChild(baseType); if (result != null) return result; baseType = baseType.BetterResolve().BaseType; }; } return module.ImportReference(typeof(object)); }
private static IEnumerable <TypeReference> GetGenericInstances(this TypeReference type, string[] genericArgumentNames, TypeReference[] genericArgumentsOfCurrentType) { var resolvedBase = type.BetterResolve(); if (resolvedBase.HasGenericParameters) { var genericArguments = new List <TypeReference>(); foreach (var arg in (type as GenericInstanceType).GenericArguments) { var t = genericArgumentNames.FirstOrDefault(x => x == arg.FullName); if (t == null) { genericArguments.Add(arg); } else { genericArguments.Add(genericArgumentsOfCurrentType[Array.IndexOf(genericArgumentNames, t)]); } } var genericType = resolvedBase.MakeGenericInstanceType(genericArguments.ToArray()); return(genericType.GetGenericInstances()); } return(new TypeReference[0]); }
internal BuilderType(BuilderType builderType, TypeReference typeReference) : base(builderType) { this.IsByReference = typeReference.IsByReference; this.typeReference = typeReference; this.typeDefinition = typeReference.BetterResolve(); this.Builder = builderType.Builder; }
public static IEnumerable<TypeReference> GetInterfaces(this TypeReference type) { var typeDef = type.BetterResolve(); var result = new List<TypeReference>(); while (true) { if (typeDef == null) break; try { if (typeDef.BaseType == null && (typeDef.Interfaces == null || typeDef.Interfaces.Count == 0)) break; if (typeDef.Interfaces != null && typeDef.Interfaces.Count > 0) result.AddRange(type.Recursive(x => x.BetterResolve().Interfaces.Select(y => y.InterfaceType)).Select(x => x.ResolveType(type))); type = typeDef.BaseType; typeDef = type?.BetterResolve(); } catch { break; } }; return result; }
private static void GetMethodReferences(TypeReference typeToInspect, List <MethodReference> result, bool byInterfaces) { if (typeToInspect == null) { return; } if (typeToInspect.IsGenericInstance) { var genericType = typeToInspect as GenericInstanceType; if (genericType != null) { var instances = genericType.GetGenericInstances().Where(x => (!x.BetterResolve().IsInterface || byInterfaces)); foreach (var item in instances) { var methods = item.BetterResolve().Methods.Select(x => x.MakeHostInstanceGeneric((item as GenericInstanceType).GenericArguments.ToArray())); if (methods != null || methods.Any()) { result.AddRange(methods); } } } } else { var methods = typeToInspect.BetterResolve().Methods; if (methods != null || methods.Count > 0) { result.AddRange(methods); } } var typeReference = typeToInspect.BetterResolve(); if (byInterfaces) { for (int i = 0; i < typeReference.Interfaces.Count; i++) { GetMethodReferences(typeReference.Interfaces[i].InterfaceType, result, true); } } else if (typeReference.BaseType != null) { GetMethodReferences(typeReference.BaseType, result, false); } }
public static IEnumerable<TypeReference> GetBaseClasses(this TypeReference type) { var typeDef = type.BetterResolve(); if (typeDef != null && typeDef.BaseType != null) { yield return typeDef.BaseType; foreach (var item in GetBaseClasses(typeDef.BaseType)) yield return item; } }
public static MethodReference GetMethodReference(this TypeReference type, string methodName, Type[] parameterTypes) { var definition = type.BetterResolve(); var result = definition .Methods .FirstOrDefault(x => x.Name == methodName && parameterTypes.Select(y => y.FullName).SequenceEqual(x.Parameters.Select(y => y.ParameterType.FullName))); if (result != null) return result; throw new Exception($"Unable to proceed. The type '{type.FullName}' does not contain a method '{methodName}'"); }
public static MethodReference GetMethodReference(this TypeReference type, string methodName, int parameterCount) { var definition = type.BetterResolve(); var result = definition .Methods .FirstOrDefault(x => x.Name == methodName && x.Parameters.Count == parameterCount); if (result != null) return result; throw new Exception($"Unable to proceed. The type '{type.FullName}' does not contain a method '{methodName}'"); }
public static IEnumerable<TypeReference> GetNestedTypes(this TypeReference type) { var typeDef = type.BetterResolve(); if (typeDef == null) return new TypeReference[0]; if (typeDef.NestedTypes != null && typeDef.NestedTypes.Count > 0) return type.Recursive(x => x.BetterResolve().NestedTypes).Select(x => x.ResolveType(type)); if (typeDef.BaseType != null) return GetNestedTypes(typeDef.BaseType); return new TypeReference[0]; }
internal static bool IsDelegate(this TypeReference typeReference) => typeReference.BetterResolve().IsDelegate();
public static bool IsAssignableFrom(this TypeReference target, TypeReference source) => target == source || target == source || source.IsSubclassOf(target) || target.BetterResolve().IsInterface&& source.GetBaseClasses().Any(x => x.Implements(target.FullName));
private static IEnumerable <TypeDeclaringType> GetTypeReference(TypeReference typeReference) { var typeDefinition = typeReference.BetterResolve() ?? typeReference as TypeDefinition; yield return(new TypeDeclaringType(typeReference, typeReference)); foreach (var item in typeDefinition.CustomAttributes) { yield return(new TypeDeclaringType(typeReference, item.AttributeType)); } foreach (var field in typeDefinition.Fields) { foreach (var item in field.CustomAttributes) { yield return(new TypeDeclaringType(typeReference, item.AttributeType)); } yield return(new TypeDeclaringType(typeReference, field.FieldType)); } foreach (var property in typeDefinition.Properties) { foreach (var item in property.CustomAttributes) { yield return(new TypeDeclaringType(typeReference, item.AttributeType)); } yield return(new TypeDeclaringType(typeReference, property.PropertyType)); } foreach (var method in typeDefinition.Methods) { foreach (var item in method.CustomAttributes) { yield return(new TypeDeclaringType(typeReference, item.AttributeType)); foreach (var @param in item.ConstructorArguments.Where(x => x.Value is TypeReference)) { yield return(new TypeDeclaringType(typeReference, param.Value as TypeReference)); } foreach (var @param in item.Fields.Where(x => x.Argument.Value is TypeReference)) { yield return(new TypeDeclaringType(typeReference, param.Argument.Value as TypeReference)); } foreach (var @param in item.Properties.Where(x => x.Argument.Value is TypeReference)) { yield return(new TypeDeclaringType(typeReference, param.Argument.Value as TypeReference)); } } if (method.ReturnType.FullName != "System.Void") { yield return(new TypeDeclaringType(typeReference, method.ReturnType)); } foreach (var item in method.Parameters) { yield return(new TypeDeclaringType(typeReference, item.ParameterType)); } foreach (var item in method.GenericParameters) { yield return(new TypeDeclaringType(typeReference, item)); } } foreach (var @event in typeDefinition.Events) { foreach (var item in @event.CustomAttributes) { yield return(new TypeDeclaringType(typeReference, item.AttributeType)); } yield return(new TypeDeclaringType(typeReference, @event.EventType)); } }
public static bool IsUsed(TypeReference typeReference) { var declaringType = typeReference.BetterResolve(); return (Types .Any(x => { if (x.declaringType.AreEqual(typeReference)) { return false; } if (x.typeReference.AreEqual(typeReference)) { if (declaringType.HasNestedTypes && x.declaringType.IsNested) { return false; } return true; } return false; }) || declaringType .Methods .SelectMany(methodDefinition => Bucket .Where(x => { if (x == null) { return false; } if (methodDefinition == null) { return false; } if (x.instruction.OpCode != OpCodes.Call && x.instruction.OpCode != OpCodes.Callvirt && x.instruction.OpCode == OpCodes.Newobj) { return false; } if (x.instruction.Operand == null) { return false; } if (x.method.DeclaringType.AreEqual(typeReference)) { return false; } var value = (x.instruction.Operand as MethodReference)?.BetterResolve(); if (value == null) { return false; } return value.AreEqual(methodDefinition); })) .Any()); }