Ejemplo n.º 1
0
        public MethodReference Retarget(MethodReference method, GenericContext context)
        {
            MethodReference reference;

            if (method.IsDefinition && Utility.SameScope(method.DeclaringType.Scope, this.Module))
            {
                reference = method;
            }
            else if (method.IsGenericInstance)
            {
                GenericInstanceMethod method2 = (GenericInstanceMethod)method;
                GenericInstanceMethod method3 = new GenericInstanceMethod(this.Retarget(method2.ElementMethod, context));
                foreach (TypeReference reference2 in method2.GenericArguments)
                {
                    TypeReference item = this.Retarget(reference2, context);
                    method3.GenericArguments.Add(item);
                }
                reference = method3;
            }
            else
            {
                TypeReference declaringType = this.Retarget(method.DeclaringType, context);
                context.PushType(declaringType.GetElementType());
                MethodReference owner = new MethodReference(method.Name, method.ReturnType, declaringType)
                {
                    CallingConvention = method.CallingConvention,
                    ExplicitThis      = method.ExplicitThis,
                    HasThis           = method.HasThis
                };
                using (Collection <GenericParameter> .Enumerator enumerator2 = method.GenericParameters.GetEnumerator())
                {
                    while (enumerator2.MoveNext())
                    {
                        GenericParameter parameter = new GenericParameter(enumerator2.Current.Name, owner);
                        owner.GenericParameters.Add(parameter);
                    }
                }
                context.PushMethod(owner);
                owner.ReturnType = this.Retarget(method.ReturnType, context);
                foreach (ParameterDefinition definition in method.Parameters)
                {
                    TypeReference       parameterType = this.Retarget(definition.ParameterType, context);
                    ParameterDefinition definition2   = new ParameterDefinition(definition.Name, definition.Attributes, parameterType);
                    owner.Parameters.Add(definition2);
                }
                reference = owner;
                context.PopMethod();
                context.PopType();
            }
            return(this.Module.ImportReference(reference));
        }
 private void Visit(MethodDefinition method, GenericContext context)
 {
     try
     {
         context.PushMethod(method);
         this.Visit((ICustomAttributeProvider)method, context);
         this.Visit(method.GenericParameters, context);
         this.Visit(method.MethodReturnType, context);
         method.ReturnType = base.ModuleContext.Retarget(method.ReturnType, context);
         for (int i = 0; i < method.Parameters.Count; i++)
         {
             this.Visit(method.Parameters[i], context);
             method.Parameters[i].ParameterType = base.ModuleContext.Retarget(method.Parameters[i].ParameterType, context);
         }
         for (int j = 0; j < method.Overrides.Count; j++)
         {
             method.Overrides[j] = base.ModuleContext.Retarget(method.Overrides[j], context);
         }
         if (method.HasBody)
         {
             foreach (ExceptionHandler handler in method.Body.ExceptionHandlers)
             {
                 handler.CatchType = base.ModuleContext.Retarget(handler.CatchType, context);
             }
             foreach (VariableDefinition definition in method.Body.Variables)
             {
                 definition.VariableType = base.ModuleContext.Retarget(definition.VariableType, context);
             }
             foreach (Instruction instruction in method.Body.Instructions)
             {
                 MemberReference operand = instruction.Operand as MemberReference;
                 if (operand != null)
                 {
                     MethodReference reference3 = operand as MethodReference;
                     if (reference3 == null)
                     {
                         FieldReference field = operand as FieldReference;
                         if (field == null)
                         {
                             TypeReference type = operand as TypeReference;
                             if (type == null)
                             {
                                 throw new NotImplementedException();
                             }
                             instruction.Operand = base.ModuleContext.Retarget(type, context);
                         }
                         else
                         {
                             instruction.Operand = base.ModuleContext.Retarget(field, context);
                         }
                     }
                     else
                     {
                         instruction.Operand = base.ModuleContext.Retarget(reference3, context);
                     }
                 }
                 else
                 {
                     ParameterReference reference2 = instruction.Operand as ParameterReference;
                     if (reference2 != null)
                     {
                         reference2.ParameterType = base.ModuleContext.Retarget(reference2.ParameterType, context);
                     }
                 }
             }
             context.PopMethod();
         }
     }
     catch
     {
         Console.Error.WriteLine("Failed to fix references for method {0}", method.FullName);
         throw;
     }
 }