コード例 #1
0
        public IMethodReturn Invoke(IMethodInvocation input,
                                    InvokeHandlerDelegate target)
        {
            if (handlers.Count == 0)
            {
                return(target(input, null));
            }

            int handlerIndex = 0;

            IMethodReturn result = handlers[0].Invoke(input, delegate
            {
                ++handlerIndex;

                if (handlerIndex < handlers.Count)
                {
                    return(handlers[handlerIndex].Invoke);
                }
                else
                {
                    return(target);
                }
            });

            return(result);
        }
コード例 #2
0
        public IMethodReturn Invoke(IMethodInvocation input, GetNextHandlerDelegate getNext)
        {
            Console.WriteLine("Called: {0}.{1}", input.Target.GetType(), input.MethodBase.Name);
            if (input.Arguments.Count > 0)
            {
                Console.WriteLine("\tWith Arguments");
                for (int i = 0; i < input.Arguments.Count; i++)
                {
                    Console.WriteLine("\t\tName:" + input.Arguments.ParameterName(i));
                }
            }

            InvokeHandlerDelegate next = getNext();

            Console.WriteLine("Execute...");
            IMethodReturn methodReturn = next(input, getNext);

            string result = methodReturn.ReturnValue == null ? "(void)" : methodReturn.ReturnValue.ToString();

            if (methodReturn.Exception != null)
            {
                Console.WriteLine("Exception: {0}", methodReturn.Exception);
            }

            Console.WriteLine("Result: {0}", result);

            return(methodReturn);
        }
コード例 #3
0
 private static void RegisterCLREvent(string eventId,
                                      Type handlerType, InvokeHandlerDelegate invoker)
 {
     _handlerTypes.Add(Key(eventId), new HandlerInfo
     {
         Type = handlerType, Invoker = invoker
     });
 }
コード例 #4
0
 private static void RegisterRoutedEvent(RoutedEvent routedEvent,
                                         Type handlerType, InvokeHandlerDelegate invoker)
 {
     _handlerTypes.Add(Key(routedEvent), new HandlerInfo
     {
         Type = handlerType, Invoker = invoker
     });
 }
コード例 #5
0
ファイル: ProxyBuilder.cs プロジェクト: ClockGet/SimpleAOP
        public InvokeHandlerDelegate Build()
        {
            InvokeHandlerDelegate @delegate = _last;

            foreach (var d in delegateList.Reverse())
            {
                @delegate = d(@delegate);
            }
            return(@delegate);
        }
コード例 #6
0
ファイル: HandlerPipeline.cs プロジェクト: kangkot/unity
        /// <summary>
        /// Execute the pipeline with the given input.
        /// </summary>
        /// <param name="input">Input to the method call.</param>
        /// <param name="target">The ultimate target of the call.</param>
        /// <returns>Return value from the pipeline.</returns>
        public IMethodReturn Invoke(IMethodInvocation input, InvokeHandlerDelegate target)
        {
            if (handlers.Count == 0)
            {
                return target(input, null);
            }

            int handlerIndex = 0;

            IMethodReturn result = handlers[0].Invoke(input, delegate
                                      {
                                          ++handlerIndex;
                                          if (handlerIndex < handlers.Count)
                                          {
                                              return handlers[handlerIndex].Invoke;
                                          }
                                          else
                                          {
                                              return target;
                                          }
                                      });
            return result;
        }
コード例 #7
0
        public IMethodReturn Invoke(IMethodInvocation input, GetNextHandlerDelegate getNext)
        {
            InvokeHandlerDelegate next = getNext();

            return(next(input, getNext));
        }
コード例 #8
0
 private static void AddCLREvent(string eventId, Type handlerType,
                                 InvokeHandlerDelegate invoker)
 {
 }
コード例 #9
0
        /*Derived Method process:
         * baseMethod.ReturnType DerivedMethod(baseMethod.Parameters)
         * {
         *     IMethodInvocation input = Wrapped(baseMethod.Parameters);
         *     var methodReturn = @delegate(input);
         *     if(methodReturn.Exception==null)
         *         return (baseMethod.ReturnType)methodReturn.ReturnValue;
         *     throw methodReturn.Exception;
         * }
         */
        private void AddMethod(MethodInfo methodInfo, InvokeHandlerDelegate @delegate)
        {
            var attr          = methodInfo.Attributes & ~MethodAttributes.VtableLayoutMask & ~MethodAttributes.Abstract;
            var methodBuilder = _typeBuilder.DefineMethod(methodInfo.Name, attr);

            Type declaringType = methodInfo.DeclaringType;
            GenericParameterMapper        mapper     = (declaringType.IsGenericType && declaringType != methodInfo.ReflectedType) ? new GenericParameterMapper(declaringType, _targetTypeParameterMapper) : _targetTypeParameterMapper;
            MethodOverrideParameterMapper paraMapper = new MethodOverrideParameterMapper(methodInfo);

            paraMapper.SetupParameters(methodBuilder, mapper);
            methodBuilder.SetReturnType(paraMapper.GetReturnType());
            methodBuilder.SetParameters(methodInfo.GetParameters().Select(pi => paraMapper.GetParameterType(pi.ParameterType)).ToArray());
            var il = methodBuilder.GetILGenerator();

            il.DeclareLocal(typeof(ProxyDelegate));     //local 0
            il.DeclareLocal(typeof(MethodInvocation));  //local 1
            il.DeclareLocal(typeof(IMethodReturn));     //local 2
            //add ProxyDelegate to ProxyMap
            _proxyDelegates.Add(new ProxyDelegate {
                @delegate = @delegate, methodInfo = methodInfo
            });

            var parameterInfos  = methodInfo.GetParameters();
            int parameterLength = parameterInfos.Length;
            int paramNum        = 1;

            foreach (ParameterInfo pi2 in parameterInfos)
            {
                methodBuilder.DefineParameter(paramNum++, pi2.Attributes, pi2.Name);
            }
            //the ref parameter(ref or out) set a default value
            for (int i = 0; i < parameterLength; i++)
            {
                if (paraMapper.GetParameterType(parameterInfos[i].ParameterType).IsByRef)
                {
                    EmitLoadArgument(il, i);
                    il.Emit(OpCodes.Initobj, paraMapper.GetElementType(parameterInfos[i].ParameterType));
                }
            }
            //ProxyDelegate proxyDelegate=ProxyMap<$Type>.Map[$methodCount];
            il.Emit(OpCodes.Ldsfld, _mapFieldInfo);
            EmitLoadConstant(il, methodCount);
            il.Emit(OpCodes.Callvirt, _mapGetMethod);
            il.Emit(OpCodes.Stloc_0);   //set the value to local 0

            il.Emit(OpCodes.Ldarg_0);   //load this
            il.Emit(OpCodes.Ldloc_0);   //load local 0
            il.Emit(OpCodes.Ldfld, typeof(ProxyDelegate).GetField("methodInfo"));

            //new object[]
            EmitLoadConstant(il, parameterLength);
            il.Emit(OpCodes.Newarr, typeof(object));

            for (int i = 0; i < parameterLength; i++)
            {
                il.Emit(OpCodes.Dup);//copy the value to the top of the stack
                EmitLoadConstant(il, i);
                EmitLoadArgument(il, i);
                var parameterType = paraMapper.GetParameterType(parameterInfos[i].ParameterType);
                var isByRef       = parameterType.IsByRef;
                if (isByRef)
                {
                    parameterType = parameterType.GetElementType();
                }
                if (parameterInfos[i].ParameterType.IsValueType || parameterInfos[i].ParameterType.IsGenericParameter)
                {
                    il.Emit(OpCodes.Box, paraMapper.GetParameterType(parameterInfos[i].ParameterType));
                }
                else if (isByRef)
                {
                    il.Emit(OpCodes.Ldobj, parameterType);
                    if (parameterType.IsValueType || parameterType.IsGenericParameter)
                    {
                        il.Emit(OpCodes.Box, parameterType);
                    }
                }
                il.Emit(OpCodes.Stelem_Ref);
            }
            il.Emit(OpCodes.Newobj, typeof(MethodInvocation).GetConstructor(new Type[] { typeof(object), typeof(MethodBase), typeof(object[]) })); //call new MethodInvocation()
            il.Emit(OpCodes.Stloc_1);                                                                                                              //set new obj to local 1
            //IMethodReturn r=proxyDelegate.@delegate(input)
            il.Emit(OpCodes.Ldloc_0);
            il.Emit(OpCodes.Ldfld, typeof(ProxyDelegate).GetField("delegate"));
            il.Emit(OpCodes.Ldloc_1);
            il.Emit(OpCodes.Callvirt, @delegate.GetType().GetMethod("Invoke"));
            il.Emit(OpCodes.Stloc_2);
            // if (r.Exception==null)
            il.Emit(OpCodes.Ldloc_2);
            il.Emit(OpCodes.Callvirt, typeof(IMethodReturn).GetMethod("get_Exception", BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance));
            Label lbTrue = il.DefineLabel();

            il.Emit(OpCodes.Brtrue_S, lbTrue);
            //false
            //handle ref or out parameters
            var getOutputs   = typeof(IMethodReturn).GetMethod("get_Outputs", BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance);
            var getItem      = typeof(IParameterCollection).GetMethod("get_Item", BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance, null, new Type[] { typeof(int) }, new ParameterModifier[0]);
            int refParamNums = 0;

            for (int i = 0; i < parameterLength; i++)
            {
                var parameterType = paraMapper.GetParameterType(parameterInfos[i].ParameterType);
                if (parameterType.IsByRef)
                {
                    EmitLoadArgument(il, i);
                    il.Emit(OpCodes.Ldloc_2);
                    il.Emit(OpCodes.Callvirt, getOutputs);
                    EmitLoadConstant(il, refParamNums++);
                    il.Emit(OpCodes.Callvirt, getItem);
                    var elementType = parameterType.GetElementType();
                    if (elementType.IsValueType || elementType.IsGenericParameter)
                    {
                        il.Emit(OpCodes.Unbox_Any, elementType);
                    }
                    else
                    {
                        il.Emit(OpCodes.Castclass, elementType);
                    }
                    il.Emit(OpCodes.Stobj, elementType);
                }
            }
            //return ($ReturnType)r.ReturnValue;
            var returnType = paraMapper.GetReturnType();

            if (returnType != typeof(void))
            {
                il.Emit(OpCodes.Ldloc_2);
                il.Emit(OpCodes.Callvirt, typeof(IMethodReturn).GetMethod("get_ReturnValue"));
                if (returnType.IsValueType || returnType.IsGenericParameter)
                {
                    il.Emit(OpCodes.Unbox_Any, returnType);
                }
                else
                {
                    il.Emit(OpCodes.Castclass, returnType);
                }
            }
            il.Emit(OpCodes.Ret);
            //ture
            //throw r.Exception
            il.MarkLabel(lbTrue);
            il.Emit(OpCodes.Ldloc_2);
            il.Emit(OpCodes.Callvirt, typeof(IMethodReturn).GetMethod("get_Exception", BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance));
            il.Emit(OpCodes.Throw);
            //increase methodCount
            methodCount++;
        }
コード例 #10
0
ファイル: ProxyBuilder.cs プロジェクト: ClockGet/SimpleAOP
 public ProxyBuilder(InvokeHandlerDelegate last)
 {
     _last = last;
 }