예제 #1
0
        public CallWriter(Stream stream, Type modelInterface)
        {
            this.stream = stream;

            this.modelInterface = modelInterface;

            returnTypes = modelInterface.AllMethods().ToDictionary(x => DynamicWrapper.MethodSerialize(x), x => x.ReturnType);

            new Thread(ReturnReadLoop).Start();
        }
예제 #2
0
        public void Generate(MethodInfo method)
        {
            if (method.IsGenericMethod)
            {
                method = method.GetGenericMethodDefinition();
            }


            var parameters     = method.GetParameters();
            var parameterTypes = parameters.Select(parameter => parameter.ParameterType).ToArray();

            var methodBuilder = _wrapperBuilder.DefineMethod(
                method.Name,
                MethodAttributes.Public | MethodAttributes.Virtual,
                method.ReturnType,
                parameterTypes);

            if (method.IsGenericMethod)
            {
                methodBuilder.DefineGenericParameters(
                    method.GetGenericArguments().Select(arg => arg.Name).ToArray());
            }

            ILGenerator ilGenerator = methodBuilder.GetILGenerator();

            // Push ModelHolder onto the stack
            // Call ModelHolder
            ilGenerator.Emit(OpCodes.Ldarg_0);
            ilGenerator.Emit(OpCodes.Call, typeof(ModelBase).GetProperties().Where(x => x.Name == "ModelHolder").First().GetMethod);

            // Push the function name on the stack
            ilGenerator.Emit(OpCodes.Ldstr, DynamicWrapper.MethodSerialize(method));

            //ilGenerator.Emit(OpCodes.Ldstr, method.Name);

            // Push object[] paramseters
            // Create object[] array
            ilGenerator.Emit(OpCodes.Ldc_I4_S, parameters.Length);
            ilGenerator.Emit(OpCodes.Newarr, typeof(object));

            // Set values in array
            for (int i = 0; i < parameters.Length; i++)
            {
                ilGenerator.Emit(OpCodes.Dup);
                ilGenerator.Emit(OpCodes.Ldc_I4_S, i);

                Type type = parameters[i].ParameterType;
                ilGenerator.Emit(OpCodes.Ldarg, i + 1);
                if (type.IsPrimitive)
                {
                    ilGenerator.Emit(OpCodes.Box, type);
                }
                //Put stack value into array position
                ilGenerator.Emit(OpCodes.Stelem_Ref);
            }

            var methodCall = typeof(IModelHolder).GetMethod("MethodCall");

            ilGenerator.EmitCall(OpCodes.Callvirt, methodCall, new Type[] { typeof(string), typeof(object[]) });

            if (method.ReturnType != typeof(void))
            {
                if (method.ReturnType.IsPrimitive)
                {
                    ilGenerator.Emit(OpCodes.Unbox_Any, method.ReturnType);
                }
                else if (method.ReturnType != typeof(object))
                {
                    ilGenerator.Emit(OpCodes.Castclass, method.ReturnType);
                }
            }
            else
            {
                ilGenerator.Emit(OpCodes.Pop);
            }

            ilGenerator.Emit(OpCodes.Ret);
        }
예제 #3
0
        public CallReader(Stream stream, object instance)
        {
            this.stream   = stream;
            this.instance = instance;

            methods     = instance.GetType().AllMethods().Where(x => !x.IsAbstract).ToDictionary(x => DynamicWrapper.MethodSerialize(x), x => new FastMethodInfo(x));
            returnTypes = instance.GetType().AllMethods().Where(x => !x.IsAbstract).ToDictionary(x => DynamicWrapper.MethodSerialize(x), x => x.ReturnType);

            new Thread(ReadLoop).Start();
        }