internal SharedDelegate(MethodInfo info, SharedClass sharedClass, Type DelegateType, int DelegateId, Delegate Delegate, int MethodId)
 {
     this.sharedMethod          = new SharedMethod(info, sharedClass, true, DelegateId);
     this.DelegateType          = DelegateType;
     this.Delegate              = Delegate;
     this.sharedMethod.MethodId = MethodId;
 }
Exemplo n.º 2
0
        public object Invoke(int MethodId, params object[] args)
        {
            if (IsDisposed)
            {
                throw new Exception("The shared class is disposed");
            }

            SharedMethod method = GetMethod(MethodId);

            lock (method.InvokeLocky)
            {
                ReturnResult ret = method.Invoke(args) as ReturnResult;

                if (ret != null)
                {
                    if (ret.ExceptionOccured)
                    {
                        throw new Exception(ret.exceptionMessage);
                    }
                    return(ret.ReturnValue);
                }
                return(null);
            }
            throw new Exception("Method not found");
        }
Exemplo n.º 3
0
        private static void DuplicateMethods(TypeBuilder typeBuilder, Type target, FieldBuilder fb, SharedClass sharedClass)
        {
            foreach (MethodInfo m in target.GetMethods())
            {
                /*if ((m.GetCustomAttributes(typeof(RemoteExecutionAttribute), false).Length == 0 &&
                 *  m.GetCustomAttributes(typeof(UncheckedRemoteExecutionAttribute), false).Length == 0) &&
                 *  m.Name != "Dispose")
                 * {
                 *  continue;
                 * }*/

                Type[]        ArgumentTypes = GetParameterTypes(m.GetParameters());
                MethodBuilder builder       = typeBuilder.DefineMethod(m.Name, MethodAttributes.Public | MethodAttributes.Virtual | MethodAttributes.HideBySig, m.CallingConvention, m.ReturnType, ArgumentTypes);
                typeBuilder.DefineMethodOverride(builder, m);

                //builder.CreateMethodBody(null, 0);
                ILGenerator gen = builder.GetILGenerator();

                MethodInfo   SharedCall   = typeof(SharedClass).GetMethod("Invoke", new Type[] { typeof(int), typeof(object[]) });
                SharedMethod sharedMethod = sharedClass.GetMethod(m.Name, ArgumentTypes);
                LocalBuilder lb           = gen.DeclareLocal(typeof(object[]));

                if (sharedMethod == null)
                {
                    throw new Exception("Missing a method \"" + m.Name + "\" check your shared class!");
                }

                //load $haredClass
                gen.Emit(OpCodes.Ldarg_0);
                gen.Emit(OpCodes.Ldfld, fb);

                gen.Emit(OpCodes.Ldc_I4, sharedMethod.MethodId);
                //gen.Emit(OpCodes.Ldstr, m.Name);

                //init local array
                gen.Emit(OpCodes.Ldc_I4, ArgumentTypes.Length);
                gen.Emit(OpCodes.Newarr, typeof(object));
                gen.Emit(OpCodes.Stloc_0);

                for (int i = 0; i < ArgumentTypes.Length; i++)
                {
                    gen.Emit(OpCodes.Ldloc_0);
                    gen.Emit(OpCodes.Ldc_I4, i);
                    gen.Emit(OpCodes.Ldarg, i + 1);

                    if (ArgumentTypes[i].IsByRef)
                    {
                        //remove & at the end since ref/out adds & at the end of the argument
                        ArgumentTypes[i] = Type.GetType(ArgumentTypes[i].FullName.Substring(0, ArgumentTypes[i].FullName.Length - 1));
                    }

                    gen.Emit(OpCodes.Box, ArgumentTypes[i]);
                    gen.Emit(OpCodes.Stelem_Ref);
                }

                gen.Emit(OpCodes.Ldloc_0);
                gen.Emit(OpCodes.Callvirt, SharedCall);

                bool isInt = m.ReturnType.IsAssignableFrom(typeof(System.Int32)) ||
                             m.ReturnType.IsAssignableFrom(typeof(System.UInt32)) ||
                             m.ReturnType.IsAssignableFrom(typeof(System.Boolean)) ||
                             m.ReturnType.IsAssignableFrom(typeof(System.Int64)) ||
                             m.ReturnType.IsAssignableFrom(typeof(System.UInt64));

                if (m.ReturnType.FullName != "System.Void" && !isInt)
                {
                    gen.Emit(OpCodes.Box, m.ReturnType);
                }
                else if (m.ReturnType.FullName == "System.Void") //no return
                {
                    gen.Emit(OpCodes.Pop);
                }
                else if (isInt)
                {
                    gen.Emit(OpCodes.Unbox, m.ReturnType);
                    gen.Emit(OpCodes.Ldobj, m.ReturnType);
                }
                gen.Emit(OpCodes.Ret);
            }
        }
Exemplo n.º 4
0
        /// <summary>  </summary>
        /// <param name="Object">The Class object to share with others</param>
        /// <param name="RemoteInitialize">False: The class will be initialized locally using the "ClassArgs" objects,
        ///                                True: The remote client will give the ClassArgs to use for initializing the object and will ignore the local argument objects</param>
        /// <param name="ClassArgs">The objects to initialize the class with</param>
        /// <param name="MaxInitializations">The maximum count that the class can be shared </param>
        internal SharedClass(string SharedName, Type ClassType, IClient Client, bool RemoteInitialize = false, int MaxInitializations = 100, params object[] ClassArgs)
        {
            if (ClassType == null)
            {
                throw new ArgumentNullException("Object");
            }
            if (!ClassType.IsClass)
            {
                throw new Exception("Object is not a class");
            }

            this._Methods          = new SortedList <string, List <SharedMethod> >();
            this.BaseClassType     = ClassType;
            this.BaseClassTypeArgs = ClassArgs;

            if (this.BaseClassTypeArgs == null)
            {
                this.BaseClassTypeArgs = new object[0];
            }

            this.TypeName           = ClassType.FullName;
            this.SharedName         = SharedName;
            this.Client             = Client;
            this.ConstructorTypes   = new List <Type[]>();
            this.RemoteInitialize   = RemoteInitialize;
            this.MaxInitializations = MaxInitializations;

            List <SharedMethod> methods = new List <SharedMethod>();

            foreach (MethodInfo m in ClassType.GetMethods())
            {
                if (!m.IsPublic || m.GetCustomAttributes(typeof(RemoteExecutionAttribute), false).Length == 0 &&
                    m.GetCustomAttributes(typeof(UncheckedRemoteExecutionAttribute), false).Length == 0)
                {
                    continue;
                }

                SharedMethod sharedMethod = new SharedMethod(m, this);

                if (!_Methods.ContainsKey(m.Name))
                {
                    _Methods.Add(m.Name, new List <SharedMethod>());
                }
                _Methods[m.Name].Add(sharedMethod);

                methods.Add(sharedMethod);
                sharedMethod.MethodId = methods.Count;
            }
            this.Methods = methods.ToArray();

            foreach (ConstructorInfo m in ClassType.GetConstructors())
            {
                if (!m.IsStatic && m.IsPublic && m.GetCustomAttributes(typeof(RemoteConstructorAttribute), false).Length > 0)
                {
                    List <Type> list = new List <Type>();
                    foreach (ParameterInfo param in m.GetParameters())
                    {
                        list.Add(param.ParameterType);
                    }
                    ConstructorTypes.Add(list.ToArray());
                }
            }
        }