/// <summary>
        /// 创建指定 <paramref name="constructorInfo"/> 的动态构造函数。
        /// </summary>
        /// <param name="constructorInfo">构造函数的元数据。</param>
        /// <param name="declaringType">声明该成员的类。</param>
        /// <returns>返回一个绑定到实例构造函数的委托。</returns>
        protected override DynamicConstructorHandler CreateHandler(ConstructorInfo constructorInfo, Type declaringType)
        {
            if (declaringType.IsValueType)
            {
                return((parameters) =>
                {
                    return Activator.CreateInstance(declaringType, parameters);
                });
            }
            ParameterInfo[] parameterInfos = constructorInfo.GetParameters();
            int             paramterLength = parameterInfos.Length;


            EmitHelper emit = new EmitHelper(string.Empty,
                                             Types.Object,
                                             new Type[1] {
                Types.ObjectArray
            },
                                             declaringType,
                                             SkipVisibility, true);

            Type[]         paramTypes = new Type[paramterLength];
            LocalBuilder[] locals     = new LocalBuilder[paramterLength];

            if (paramterLength > 0)
            {
                for (int i = 0; i < paramterLength; i++)
                {
                    if (parameterInfos[i].ParameterType.IsByRef)
                    {
                        paramTypes[i] = parameterInfos[i].ParameterType.GetElementType();
                    }
                    else
                    {
                        paramTypes[i] = parameterInfos[i].ParameterType;
                    }

                    locals[i] = emit.DeclareLocal(paramTypes[i]);
                    emit.LoadArgument(0);       //- 取出参数0 也就是 object[]
                    emit.LoadConstant(i);       //- 指定索引号 —— 0
                    emit.LoadRefElement();      //- 取出索引元素 object[0]
                    emit.CastTo(paramTypes[i]); //- 类型转换,从 object 到指定参数类型。
                    emit.StoreLocal(locals[i]);
                }

                for (int i = 0; i < paramterLength; i++)
                {   //- 取出所有 method 函数的参数
                    if (parameterInfos[i].ParameterType.IsByRef)
                    {
                        emit.LoadLocalBySpecific(locals[i]);
                    }
                    else
                    {
                        emit.LoadLocal(locals[i]);
                    }
                }
            }
            emit.NewObject(constructorInfo);

            emit.Return();
            return(emit.CreateDelegate <DynamicConstructorHandler>());
        }
예제 #2
0
        /// <summary>
        /// 创建指定 <paramref name="methodInfo"/> 的动态方法。
        /// </summary>
        /// <param name="methodInfo">方法的元数据。</param>
        /// <param name="declaringType">声明该成员的类。</param>
        /// <returns>返回一个绑定到实例方法的委托。</returns>
        protected override DynamicMethodHandler CreateHandler(MethodInfo methodInfo, Type declaringType)
        {
            Type returnType = methodInfo.ReturnType;                      //- 方法的返回类型

            ParameterInfo[] parameterInfos = methodInfo.GetParameters();  //- 方法的参数集合
            int             paramterLength = parameterInfos.Length;

            EmitHelper emit = new EmitHelper(string.Empty,
                                             Types.Object,
                                             new Type[2] {
                Types.Object, Types.ObjectArray
            },
                                             declaringType,
                                             SkipVisibility,
                                             false);//- 为什么这里不使用 OwnerType 而使用 member.DeclaringType,主要是考虑到泛型:<object>

            Type[] paramTypes = new Type[paramterLength];

            LocalBuilder[] locals = new LocalBuilder[paramterLength];

            for (int i = 0; i < paramterLength; i++)
            {
                if (parameterInfos[i].ParameterType.IsByRef)
                {
                    paramTypes[i] = parameterInfos[i].ParameterType.GetElementType();
                }
                else
                {
                    paramTypes[i] = parameterInfos[i].ParameterType;
                }

                locals[i] = emit.DeclareLocal(paramTypes[i]);
                emit.LoadArgument(1);       //- 取出参数1 也就是 object[]
                emit.LoadConstant(i);       //- 指定索引号 —— 0
                emit.LoadRefElement();      //- 取出索引元素 object[0]
                emit.CastTo(paramTypes[i]); //- 类型转换,从 object 到指定参数类型。
                emit.StoreLocal(locals[i]);
            }

            if (!methodInfo.IsStatic)
            {
                emit.LoadThis(methodInfo);  //- 非静态,取出实例
                //emit.CastTo(member.DeclaringType);
            }

            for (int i = 0; i < paramterLength; i++)
            {   //- 取出所有 method 函数的参数
                if (parameterInfos[i].ParameterType.IsByRef)
                {
                    emit.LoadLocalBySpecific(locals[i]);
                }
                else
                {
                    emit.LoadLocal(locals[i]);
                }
            }

            emit.Call(methodInfo);

            if (returnType == typeof(void))
            {
                emit.LoadNull();
            }
            else
            {
                emit.TryBox(returnType);
            }

            for (int i = 0; i < paramterLength; i++)
            {
                if (parameterInfos[i].ParameterType.IsByRef)
                {
                    emit.LoadArgument(1);               //- 取出参数1 也就是 object[]
                    emit.LoadConstant(i);               //- 指定索引号 —— 0
                    emit.LoadLocal(locals[i]);          //- 加载指定索引的数组元素
                    emit.TryBox(locals[i].LocalType);   //- 尝试装箱  paramTypes[i]
                    emit.StoreLocalByRef();             //- 赋值给 ref 或  out
                }
            }
            emit.Return();
            return(emit.CreateDelegate <DynamicMethodHandler>());
        }