MethodInjector.InjectInterceptedMethod C# (CSharp) Метод

InjectInterceptedMethod() приватный Метод

private InjectInterceptedMethod ( TypeDefinition targetType, MethodDefinition innerOnPropertyChanged ) : MethodDefinition
targetType TypeDefinition
innerOnPropertyChanged MethodDefinition
Результат MethodDefinition
    MethodDefinition InjectInterceptedMethod(TypeDefinition targetType, MethodDefinition innerOnPropertyChanged)
    {
        delegateHolderInjector.Execute(targetType, innerOnPropertyChanged);
        var method = new MethodDefinition(eventInvokerNameResolver.EventInvokerNames.First(), GetMethodAttributes(targetType), msCoreReferenceFinder.VoidTypeReference);

        var propertyName = new ParameterDefinition("propertyName", ParameterAttributes.None, msCoreReferenceFinder.StringTypeReference);
        method.Parameters.Add(propertyName);
        if (interceptorFinder.IsBeforeAfter)
        {
            var before = new ParameterDefinition("before", ParameterAttributes.None, msCoreReferenceFinder.ObjectTypeReference);
            method.Parameters.Add(before);
            var after = new ParameterDefinition("after", ParameterAttributes.None, msCoreReferenceFinder.ObjectTypeReference);
            method.Parameters.Add(after);
        }

        var action = new VariableDefinition("firePropertyChanged", msCoreReferenceFinder.ActionTypeReference);
        method.Body.Variables.Add(action);

        var variableDefinition = new VariableDefinition("delegateHolder", delegateHolderInjector.TypeDefinition);
        method.Body.Variables.Add(variableDefinition);

        var instructions = method.Body.Instructions;

        var last = Instruction.Create(OpCodes.Ret);
        instructions.Add(Instruction.Create(OpCodes.Newobj, delegateHolderInjector.ConstructorDefinition));
        instructions.Add(Instruction.Create(OpCodes.Stloc_1));
        instructions.Add(Instruction.Create(OpCodes.Ldloc_1));
        instructions.Add(Instruction.Create(OpCodes.Ldarg_1));
        instructions.Add(Instruction.Create(OpCodes.Stfld, delegateHolderInjector.PropertyName));
        instructions.Add(Instruction.Create(OpCodes.Ldloc_1));
        instructions.Add(Instruction.Create(OpCodes.Ldarg_0));
        instructions.Add(Instruction.Create(OpCodes.Stfld, delegateHolderInjector.Target));
        instructions.Add(Instruction.Create(OpCodes.Ldloc_1));
        instructions.Add(Instruction.Create(OpCodes.Ldftn, delegateHolderInjector.MethodDefinition));
        instructions.Add(Instruction.Create(OpCodes.Newobj, msCoreReferenceFinder.ActionConstructorReference));
        instructions.Add(Instruction.Create(OpCodes.Stloc_0));
        instructions.Add(Instruction.Create(OpCodes.Ldarg_0));
        instructions.Add(Instruction.Create(OpCodes.Ldloc_0));
        instructions.Add(Instruction.Create(OpCodes.Ldloc_1));
        instructions.Add(Instruction.Create(OpCodes.Ldfld, delegateHolderInjector.PropertyName));
        if (interceptorFinder.IsBeforeAfter)
        {
            instructions.Add(Instruction.Create(OpCodes.Ldarg_2));
            instructions.Add(Instruction.Create(OpCodes.Ldarg_3));
            instructions.Add(Instruction.Create(OpCodes.Call, interceptorFinder.InterceptMethod));
        }
        else
        {
            instructions.Add(Instruction.Create(OpCodes.Call, interceptorFinder.InterceptMethod));
        }

        instructions.Add(last);
        method.Body.InitLocals = true;

        targetType.Methods.Add(method);
        return method;
    }