コード例 #1
0
        /// <summary>
        /// call the server method
        /// </summary>
        /// <typeparam name="T">any type can be used here when the server is void</typeparam>
        /// <param name="fun">data generated by Fun.fun</param>
        /// <returns>the data returned by the server is null when there is no return value</returns>
        public T Invoke <T>(ByteQue fun)
        {
            byte[] data  = new SendData(fun).ToArray();
            int    write = 0;

            while (true)
            {
                write += socket.Send(data, write, data.Length - write, SocketFlags.None);
                if (write >= data.Length)
                {
                    break;
                }
            }
            RecvBuf recv = new RecvBuf();

            byte[] buf = new byte[1024];
            while (true)
            {
                if (recv.Size.HasValue && recv.Size == recv.Len)
                {
                    break;
                }
                int read = socket.Receive(buf);
                if (read > 0)
                {
                    recv.Append(buf, read);
                }
                else
                {
                    Dispose();
                    throw new Exception("remote connection has been disconnected");
                }
            }
            ByteQue ret = recv.ByteQue;
            String  msg = ret.Pop <string>();

            if (msg != null)
            {
                throw new Exception(msg);
            }
            if (ret.Len > 0)
            {
                return(ret.Pop <T>());
            }
            return(default(T));
        }
コード例 #2
0
ファイル: Fun.cs プロジェクト: MechWipf/lrpc
        /// <summary>
        /// call the registered method
        /// </summary>
        /// <param name="que">the queue generated by fun</param>
        /// <returns>serialize error messages or call results into a queue</returns>
        public ByteQue Invoke(ByteQue que)
        {
            byte[] arr = new byte[que.PopSize()];
            for (int i = 0; i < arr.Length; ++i)
            {
                arr[i] = que.Pop <byte>();
            }
            string name = Encoding.UTF8.GetString(arr);

            if (!funs.ContainsKey(name))
            {
                return(Except(name + " function not found"));
            }
            ObjectMethod om = funs[name];

            ParameterInfo[] types = om.fun.GetParameters();
            object[]        args  = new object[types.Length];
            for (int i = 0; i < types.Length; ++i)
            {
                Type type = types[i].ParameterType;
                if (que.Len == 0)
                {
                    return(Except("error when calling function " + name + " to restore parameters to the " + i + "th parameter " + type.ToString()));
                }
                try
                {
                    args[i] = que.Pop(type);
                }
                catch (Exception e)
                {
                    return(Except("error when calling function " + name + " to restore parameters to the " + i + "th parameter " + type.ToString() + ": " + e.ToString()));
                }
            }
            if (que.Len != 0)
            {
                return(Except("error when calling function " + name + " to restore parameters"));
            }
            ByteQue ret = new ByteQue();
            object  rst;

            try
            {
                rst = om.fun.Invoke(om.obj, args);
            }
            catch (Exception e)
            {
                return(Except("error calling function " + name + " " + e.ToString()));
            }
            ret.Push(false);
            Type rtp = om.fun.ReturnType;

            if (rtp != typeof(void))
            {
                try
                {
                    ret.Push(rtp, rst);
                }
                catch (Exception e)
                {
                    return(Except("error calling function " + name + " to store result " + e.ToString()));
                }
            }
            return(ret);
        }
コード例 #3
0
ファイル: RecvBuf.cs プロジェクト: lipogem/lrpc
 /// <summary>
 /// add some data to the buffer until it reaches the specified length
 /// </summary>
 /// <param name="other">part of the data</param>
 /// <param name="length">actual data length</param>
 public void Append(byte[] other, int length)
 {
     if (length < 0)
     {
         length = other.Length;
     }
     if (size.HasValue)
     {
         if (size.Value > buff.Len)
         {
             int l = size.Value - buff.Len;
             if (l < length)
             {
                 buff.AddAll(other, 0, l);
             }
             else
             {
                 buff.AddAll(other, 0, length);
             }
         }
     }
     else
     {
         if (buff.Len == 0)
         {
             for (int x = 0; x < length; ++x)
             {
                 if (x == 4 || other[x] <= 0x7f)
                 {
                     int s = 0;
                     for (int i = 0; i <= x; ++i)
                     {
                         s |= (other[i] & 0x7f) << 7 * i;
                     }
                     size = s;
                     s   += x + 1;
                     if (s < length)
                     {
                         buff.AddAll(other, x + 1, s);
                     }
                     else
                     {
                         buff.AddAll(other, x + 1, length);
                     }
                     return;
                 }
             }
             buff.AddAll(other, 0, length);
         }
         else
         {
             buff.AddAll(other, 0, length);
             byte[] arr = buff.ToArray();
             for (int x = 0; x < arr.Length; ++x)
             {
                 if (x == 4 || arr[x] <= 0x7f)
                 {
                     int s = 0;
                     for (int i = 0; i <= x; ++i)
                     {
                         s |= (buff.Pop <byte>() & 0x7f) << 7 * i;
                     }
                     size = s;
                     s   += x + 1;
                     if (arr.Length > s)
                     {
                         buff = new ByteQue();
                         buff.AddAll(arr, x + 1, s);
                     }
                     break;
                 }
             }
         }
     }
 }