예제 #1
0
        private static MethodBuilder DefineMethodInterceptingDelegate(TypeBuilder typeBuilder, MethodInfo overridedMethod, Dictionary <Type, FieldInfo> interceptorFields, MethodInfo genericInterceptionAction, MethodInfo voidInterceptionAction, Type[] genericParameterTypes, MethodBuilder @delegate, int index, Type interceptor)
        {
            ConstructorInfo delegateConstructor;
            MethodInfo      interceptorMethod;

            // Define the method
            var method = typeBuilder.DefineMethod($"{overridedMethod.Name}-{interceptor.Name}_{index}_Interceptor",
                                                  MethodAttributes.Private | MethodAttributes.HideBySig,
                                                  overridedMethod.ReturnType,
                                                  new[] { typeof(ParamInfo[]) });

            SetupGenericMethodArguments(overridedMethod, method);

            using (var il = new GroboIL(method))
            {
                if (overridedMethod.ReturnType != typeof(void))
                {
                    interceptorMethod   = genericInterceptionAction.MakeGenericMethod(overridedMethod.ReturnType);
                    delegateConstructor = typeof(TDelegate <>).MakeGenericType(overridedMethod.ReturnType).GetConstructor(new[] { typeof(object), typeof(IntPtr) });
                }
                else
                {
                    interceptorMethod   = voidInterceptionAction;
                    delegateConstructor = typeof(VoidDelegate).GetConstructor(new[] { typeof(object), typeof(IntPtr) });
                }

                il.Ldarg(0);
                il.Ldfld(interceptorFields[interceptor]);
                il.Ldarg(0);

                if (overridedMethod.IsGenericMethodDefinition)
                {
                    il.Ldftn(@delegate.MakeGenericMethod(genericParameterTypes));
                }
                else
                {
                    il.Ldftn(@delegate);
                }

                il.Newobj(delegateConstructor);
                il.Ldarg(1);
                il.Call(interceptorMethod);
                il.Ret();

                @delegate = method;
            }

            return(@delegate);
        }
예제 #2
0
        private Func <TestClassA, int> Build1()
        {
            var typeBuilder = Module.DefineType(Guid.NewGuid().ToString(), TypeAttributes.Class | TypeAttributes.Public);
            var method      = typeBuilder.DefineMethod("zzz", MethodAttributes.Public | MethodAttributes.Static, typeof(int), new[] { typeof(TestClassA) });

            using (var il = new GroboIL(method))
            {
                il.Ldarg(0);
                il.Ldfld(typeof(TestClassA).GetField("Y"));
                var y = il.DeclareLocal(typeof(int));
                il.Stloc(y);
                il.Ldarg(0);
                il.Ldfld(typeof(TestClassA).GetField("Z"));
                var z = il.DeclareLocal(typeof(int));
                il.Stloc(z);
                il.Ldloc(y);
                il.Ldloc(z);
                il.Add();
                il.Ret();
            }
            var type          = typeBuilder.CreateType();
            var dynamicMethod = new DynamicMethod(Guid.NewGuid().ToString(), MethodAttributes.Public | MethodAttributes.Static, CallingConventions.Standard, typeof(Func <TestClassA, int>), Type.EmptyTypes, Module, true);

            using (var il = new GroboIL(dynamicMethod))
            {
                il.Ldnull();
                il.Ldftn(type.GetMethod("zzz"));
                il.Newobj(typeof(Func <TestClassA, int>).GetConstructor(new[] { typeof(object), typeof(IntPtr) }));
                il.Ret();
            }
            return(((Func <Func <TestClassA, int> >)dynamicMethod.CreateDelegate(typeof(Func <Func <TestClassA, int> >)))());
        }
예제 #3
0
        protected TDelegate CompileToMethod <TDelegate>(Expression <TDelegate> lambda, CompilerOptions options) where TDelegate : class
        {
            var typeBuilder = TestPerformance.Module.DefineType(Guid.NewGuid().ToString(), TypeAttributes.Public);
            var method      = typeBuilder.DefineMethod("lambda", MethodAttributes.Public | MethodAttributes.Static, lambda.ReturnType, lambda.Parameters.Select(parameter => parameter.Type).ToArray());

            LambdaCompiler.CompileToMethod(lambda, method, options);
            var type          = typeBuilder.CreateType();
            var dynamicMethod = new DynamicMethod(Guid.NewGuid().ToString(), MethodAttributes.Static | MethodAttributes.Public, CallingConventions.Standard, typeof(TDelegate), null, TestPerformance.Module, true);

            using (var il = new GroboIL(dynamicMethod))
            {
                il.Ldnull();
                il.Ldftn(type.GetMethod("lambda"));
                il.Newobj(typeof(TDelegate).GetConstructor(new[] { typeof(object), typeof(IntPtr) }));
                il.Ret();
            }
            return(((Func <TDelegate>)dynamicMethod.CreateDelegate(typeof(Func <TDelegate>)))());
        }