Inheritance: IMethodReturnMessage, ISerializable, IMethodMessage, IMessage, ISerializationRootObject, IMessageDictionary
コード例 #1
0
        public void ReadRequestAndWriteResponse()
        {
            IPAddress[] addressList = Dns.GetHostEntry(Environment.MachineName).AddressList;
            var endpoint = new IPEndPoint(addressList[addressList.Length - 1], 9900);
            var listener = new TcpListener(endpoint);
            listener.Start();

            var t = new Thread(new ThreadStart(() =>
            {
                var c = listener.AcceptTcpClient();
                var handle = new HttpProtocolHandle(c.GetStream());

                //read remoting request
                Trace.WriteLine(handle.ReadFirstLine());
                DumpHelper.DumpDictionary(handle.ReadHeaders());
                var messageRequest = BinaryFormatterHelper.DeserializeObject(handle.ReadContent()) as MethodCall;

                //HACK:SoapFormatter not work well
                //http://labs.developerfusion.co.uk/SourceViewer/browse.aspx?assembly=SSCLI&namespace=System.Runtime.Remoting
                //var f = new System.Runtime.Serialization.Formatters.Soap.SoapFormatter();
                //f.Context = new System.Runtime.Serialization.StreamingContext(System.Runtime.Serialization.StreamingContextStates.Other);
                //var mc = new MethodCall(this.Parse(headers));
                //var messageRequest = f.Deserialize(new System.IO.MemoryStream(content), new HeaderHandler(mc.HeaderHandler));

                Assert.IsNotNull(messageRequest);
                DumpHelper.DumpMessage(messageRequest);

                //write remoting response
                var responeMessage = new MethodResponse(new Header[] { new Header(MessageHeader.Return, messageRequest.Args[0]) }, messageRequest);
                var responseStream = BinaryFormatterHelper.SerializeObject(responeMessage);
                handle.WriteResponseFirstLine("200", "ok");
                handle.WriteHeaders(new Dictionary<string, object>() { { HttpHeader.ContentLength, responseStream.Length } });
                handle.WriteContent(responseStream);

                //end httprequest
                c.Close();
            }));
            t.Start();

            //use BinaryFormatter via HTTP
            var channel = new HttpChannel(new Hashtable(), new BinaryClientFormatterSinkProvider(), null);
            ChannelServices.RegisterChannel(channel, false);
            var url = string.Format("http://{0}/remote.rem", endpoint);
            var service = RemotingServices.Connect(typeof(ServiceClass), url) as ServiceClass;
            Assert.AreEqual("Hi", service.Do("Hi"));

            t.Abort();

            ChannelServices.UnregisterChannel(channel);
        }
コード例 #2
0
        private LogicalCallContext FetchLogicalCallContext()
        {
            ReturnMessage message = this._crmsg as ReturnMessage;

            if (message != null)
            {
                return(message.GetLogicalCallContext());
            }
            MethodResponse response = this._crmsg as MethodResponse;

            if (response == null)
            {
                throw new RemotingException(Environment.GetResourceString("Remoting_Message_BadType"));
            }
            return(response.GetLogicalCallContext());
        }
コード例 #3
0
        public void ReadRequestAndWriteResponse()
        {
            IPAddress[] addressList = Dns.GetHostEntry(Environment.MachineName).AddressList;
            var endpoint = new IPEndPoint(addressList[addressList.Length - 1], 9900);
            var listener = new TcpListener(endpoint);
            listener.Start();

            var t = new Thread(new ThreadStart(() =>
            {
                var c = listener.AcceptTcpClient();
                var handle = new TcpProtocolHandle(c.GetStream());

                //read remoting request
                Console.WriteLine("Preamble: {0}", handle.ReadPreamble());
                Console.WriteLine("MajorVersion: {0}", handle.ReadMajorVersion());
                Console.WriteLine("MinorVersion: {0}", handle.ReadMinorVersion());
                var op = handle.ReadOperation();
                Assert.AreEqual(TcpOperations.Request, op);
                Console.WriteLine("Operation: {0}", op);
                Console.WriteLine("ContentDelimiter: {0}", handle.ReadContentDelimiter());
                Console.WriteLine("ContentLength: {0}", handle.ReadContentLength());
                DumpHelper.DumpDictionary(handle.ReadTransportHeaders());
                var messageRequest = BinaryFormatterHelper.DeserializeObject(handle.ReadContent()) as MethodCall;
                Assert.IsNotNull(messageRequest);
                DumpHelper.DumpMessage(messageRequest);

                //write remoting response
                var responeMessage = new MethodResponse(new Header[] { new Header(MessageHeader.Return, messageRequest.Args[0]) }, messageRequest);
                var responseStream = BinaryFormatterHelper.SerializeObject(responeMessage);
                handle.WritePreamble();
                handle.WriteMajorVersion();
                handle.WriteMinorVersion();
                handle.WriteOperation(TcpOperations.Reply);
                handle.WriteContentDelimiter(TcpContentDelimiter.ContentLength);
                handle.WriteContentLength(responseStream.Length);
                handle.WriteTransportHeaders(null);
                handle.WriteContent(responseStream);
            }));
            t.Start();

            var url = string.Format("tcp://{0}/remote.rem", endpoint);
            var service = RemotingServices.Connect(typeof(ServiceClass), url) as ServiceClass;
            Assert.AreEqual("Hi", service.Do("Hi"));

            t.Abort();
        }
コード例 #4
0
        internal override void SetSpecialKey(int keyNum, object value)
        {
            ReturnMessage  returnMessage  = this._mrmsg as ReturnMessage;
            MethodResponse methodResponse = this._mrmsg as MethodResponse;

            if (keyNum != 0)
            {
                if (keyNum != 1)
                {
                    throw new RemotingException(Environment.GetResourceString("Remoting_Default"));
                }
                if (returnMessage != null)
                {
                    returnMessage.SetLogicalCallContext((LogicalCallContext)value);
                    return;
                }
                if (methodResponse != null)
                {
                    methodResponse.SetLogicalCallContext((LogicalCallContext)value);
                    return;
                }
                throw new RemotingException(Environment.GetResourceString("Remoting_Message_BadType"));
            }
            else
            {
                if (returnMessage != null)
                {
                    returnMessage.Uri = (string)value;
                    return;
                }
                if (methodResponse != null)
                {
                    methodResponse.Uri = (string)value;
                    return;
                }
                throw new RemotingException(Environment.GetResourceString("Remoting_Message_BadType"));
            }
        }
コード例 #5
0
		internal static IMessage CheckReturnMessage (IMessage callMsg, IMessage retMsg)
		{
#if NET_1_1
			IMethodReturnMessage ret = retMsg as IMethodReturnMessage;
			if (ret != null && ret.Exception != null)
			{
				if (RemotingConfiguration.CustomErrorsEnabled (IsLocalCall (callMsg)))
				{
					Exception ex = new Exception ("Server encountered an internal error. For more information, turn off customErrors in the server's .config file.");
					retMsg = new MethodResponse (ex, (IMethodCallMessage)callMsg);
				}
			}
#endif
			return retMsg;
		}
コード例 #6
0
ファイル: CrossAppDomainChannel.cs プロジェクト: nullie/mono
#pragma warning restore 169

		public virtual IMessage SyncProcessMessage(IMessage msgRequest) 
		{
			IMessage retMessage = null;

			try 
			{
				// Time to transit into the "our" domain
				byte [] arrResponse = null;
				byte [] arrRequest = null; 
				
				CADMethodReturnMessage cadMrm = null;
				CADMethodCallMessage cadMsg;
				
				cadMsg = CADMethodCallMessage.Create (msgRequest);
				if (null == cadMsg) {
					// Serialize the request message
					MemoryStream reqMsgStream = CADSerializer.SerializeMessage(msgRequest);
					arrRequest = reqMsgStream.GetBuffer();
				}

				Context currentContext = Thread.CurrentContext;

				try {
					// InternalInvoke can't handle out arguments, this is why
					// we return the results in a structure
					ProcessMessageRes res = (ProcessMessageRes)AppDomain.InvokeInDomainByID (_domainID, processMessageMethod, null, new object [] { arrRequest, cadMsg });
					arrResponse = res.arrResponse;
					cadMrm = res.cadMrm;
				} finally {
					AppDomain.InternalSetContext (currentContext);
				}					

				
				if (null != arrResponse) {
					// Time to deserialize the message
					MemoryStream respMsgStream = new MemoryStream(arrResponse);

					// Deserialize the response message
					retMessage = CADSerializer.DeserializeMessage(respMsgStream, msgRequest as IMethodCallMessage);
				} else
					retMessage = new MethodResponse (msgRequest as IMethodCallMessage, cadMrm);
			}
			catch (Exception e) 
			{
				try
				{
					retMessage = new ReturnMessage (e, msgRequest as IMethodCallMessage);
				}
				catch (Exception)
				{
					// this is just to be sure
				}
			}

	    	return retMessage;
		}
コード例 #7
0
ファイル: CrossAppDomainChannel.cs プロジェクト: nullie/mono
#pragma warning disable 169
		private static ProcessMessageRes ProcessMessageInDomain (
			byte[] arrRequest,
			CADMethodCallMessage cadMsg)
	    {
			ProcessMessageRes res = new ProcessMessageRes ();

			try 
			{
				AppDomain.CurrentDomain.ProcessMessageInDomain (arrRequest, cadMsg, out res.arrResponse, out res.cadMrm);
			}
			catch (Exception e) 
			{
				IMessage errorMsg = new MethodResponse (e, new ErrorMessage());
				res.arrResponse = CADSerializer.SerializeMessage (errorMsg).GetBuffer(); 
			}
			return res;
		}
コード例 #8
0
        [System.Security.SecurityCritical]  // auto-generated
        public virtual IMessage SyncProcessMessage(IMessage reqMsg) 
        {
            Message.DebugOut("\n::::::::::::::::::::::::: CrossAppDomain Channel: Sync call starting");
            IMessage errMsg = InternalSink.ValidateMessage(reqMsg);
            if (errMsg != null)
            {
                return errMsg;
            }
            

            // currentPrincipal is used to save the current principal. It should be
            //   restored on the reply message.
            IPrincipal currentPrincipal = null; 
                                      

            IMessage desRetMsg = null;

            try
            {                
                IMethodCallMessage mcmReqMsg = reqMsg as IMethodCallMessage;
                if (mcmReqMsg != null)
                {
                    LogicalCallContext lcc = mcmReqMsg.LogicalCallContext;
                    if (lcc != null)
                    {
                        // Special case Principal since if might not be serializable
                        currentPrincipal = lcc.RemovePrincipalIfNotSerializable();
                    }
                }
            
                MemoryStream reqStm = null;
                SmuggledMethodCallMessage smuggledMcm = SmuggledMethodCallMessage.SmuggleIfPossible(reqMsg);

                if (smuggledMcm == null)
                {    
            
                    //*********************** SERIALIZE REQ-MSG ****************
                    // Deserialization of objects requires permissions that users 
                    // of remoting are not guaranteed to possess. Since remoting 
                    // can guarantee that it's users can't abuse deserialization 
                    // (since it won't allow them to pass in raw blobs of 
                    // serialized data), it should assert the permissions 
                    // necessary before calling the deserialization code. This 
                    // will terminate the security stackwalk caused when 
                    // serialization checks for the correct permissions at the 
                    // remoting stack frame so the check won't continue on to 
                    // the user and fail. <EMAIL>[from Microsoft]</EMAIL>
                    // We will hold off from doing this for x-process channels
                    // until the big picture of distributed security is finalized.

                    reqStm = CrossAppDomainSerializer.SerializeMessage(reqMsg);
                }
                                
                // Retrieve calling caller context here, where it is safe from the view
                // of app domain checking code
                LogicalCallContext oldCallCtx = CallContext.SetLogicalCallContext(null);

                // Call helper method here, to avoid confusion with stack frames & app domains
                MemoryStream retStm = null;
                byte[] responseBytes = null;
                SmuggledMethodReturnMessage smuggledMrm;
                
                try
                {
                    if (smuggledMcm != null)
                        responseBytes = DoTransitionDispatch(null, smuggledMcm, out smuggledMrm);
                    else
                        responseBytes = DoTransitionDispatch(reqStm.GetBuffer(), null, out smuggledMrm);                                       
                }
                finally
                {
                    CallContext.SetLogicalCallContext(oldCallCtx);
                }

                if (smuggledMrm != null)
                {
                    ArrayList deserializedArgs = smuggledMrm.FixupForNewAppDomain();
                    desRetMsg = new MethodResponse((IMethodCallMessage)reqMsg, 
                                                   smuggledMrm,
                                                   deserializedArgs);
                }
                else
                {
                    if (responseBytes != null) {
                        retStm = new MemoryStream(responseBytes);
    
                        Message.DebugOut("::::::::::::::::::::::::::: CrossAppDomain Channel: Sync call returning!!\n");
                        //*********************** DESERIALIZE RET-MSG **************
                        desRetMsg = CrossAppDomainSerializer.DeserializeMessage(retStm, reqMsg as IMethodCallMessage);
                    }
                }
            }
            catch(Exception e)
            {
                Message.DebugOut("Arrgh.. XAppDomainSink::throwing exception " + e + "\n");
                try
                {
                    desRetMsg = new ReturnMessage(e, (reqMsg as IMethodCallMessage));
                }
                catch(Exception )
                {
                    // Fatal Error .. can't do much here
                }
            }           

            // restore the principal if necessary.
            if (currentPrincipal != null)
            {
                IMethodReturnMessage mrmRetMsg = desRetMsg as IMethodReturnMessage;
                if (mrmRetMsg != null)
                {
                    LogicalCallContext lcc = mrmRetMsg.LogicalCallContext;
                    lcc.Principal = currentPrincipal;
                }
            }           

            return desRetMsg;                         
        }
コード例 #9
0
		// used by the client
		internal IMessage FormatResponse(ISoapMessage soapMsg, IMethodCallMessage mcm) 
		{
			IMessage rtnMsg;
			
			if(soapMsg.MethodName == "Fault") {
				// an exception was thrown by the server
				Exception e = new SerializationException();
				int i = Array.IndexOf(soapMsg.ParamNames, "detail");
				if(_serverFaultExceptionField != null)
					// todo: revue this 'cause it's not safe
					e = (Exception) _serverFaultExceptionField.GetValue(
							soapMsg.ParamValues[i]);
				
				rtnMsg = new ReturnMessage((System.Exception)e, mcm);
			}
			else {
				object rtnObject = null;
				//RemMessageType messageType;
				
				// Get the output of the function if it is not *void*
				if(_methodCallInfo.ReturnType != typeof(void)){
					int index = Array.IndexOf(soapMsg.ParamNames, "return");
					rtnObject = soapMsg.ParamValues[index];
					if(rtnObject is IConvertible) 
						rtnObject = Convert.ChangeType(
								rtnObject, 
								_methodCallInfo.ReturnType);
				}
				
				object[] outParams = new object [_methodCallParameters.Length];
				int n=0;
				
				// check if there are *out* parameters
				foreach(ParameterInfo paramInfo in _methodCallParameters) {
					
					if(paramInfo.ParameterType.IsByRef || paramInfo.IsOut) {
						int index = Array.IndexOf(soapMsg.ParamNames, paramInfo.Name);
						object outParam = soapMsg.ParamValues[index];
						if(outParam is IConvertible)
							outParam = Convert.ChangeType (outParam, paramInfo.ParameterType.GetElementType());
						outParams[n] = outParam;
					}
					else
						outParams [n] = null;
					n++;
				}
				
				Header[] headers = new Header [2 + (soapMsg.Headers != null ? soapMsg.Headers.Length : 0)];
				headers [0] = new Header ("__Return", rtnObject);
				headers [1] = new Header ("__OutArgs", outParams);
				
				if (soapMsg.Headers != null)
					soapMsg.Headers.CopyTo (headers, 2);
					
				rtnMsg = new MethodResponse (headers, mcm);
			}
			return rtnMsg;
		}
コード例 #10
0
        internal static IMessage DeserializeMessage(String mimeType, Stream xstm, bool methodRequest, IMessage msg, Header[] h)
        {
            InternalRemotingServices.RemotingTrace("DeserializeMessage");
            InternalRemotingServices.RemotingTrace("MimeType: " + mimeType);

            CoreChannel.DebugOutXMLStream(xstm, "Deserializing");

            Stream fmtStm = null;

            bool bin64encode = false;
            bool doHeaderBodyAsOne = true;

            if (string.Compare(mimeType, BinaryMimeType, StringComparison.Ordinal) == 0)
            {
                doHeaderBodyAsOne = true;
            }

            if (string.Compare(mimeType, SOAPMimeType, StringComparison.Ordinal) == 0)
            {
                doHeaderBodyAsOne = false;
            }

            if (bin64encode == false)
            {
                fmtStm  = xstm;
            }
            else
            {
                InternalRemotingServices.RemotingTrace("***************** Before base64 decode *****");

                long Position = xstm.Position;
                MemoryStream inStm = (MemoryStream)xstm;
                byte[] byteArray = inStm.ToArray();
                xstm.Position = Position;

                String base64String = Encoding.ASCII.GetString(byteArray,0, byteArray.Length);

                byte[] byteArrayContent = Convert.FromBase64String(base64String);

                MemoryStream memStm = new MemoryStream(byteArrayContent);

                fmtStm = memStm;
                InternalRemotingServices.RemotingTrace("***************** after base64 decode *****");
            }

            Object ret;
            IRemotingFormatter fmt = MimeTypeToFormatter(mimeType, false);

            if (doHeaderBodyAsOne == true)
            {
                ret = ((BinaryFormatter)fmt).UnsafeDeserializeMethodResponse(fmtStm, null, (IMethodCallMessage)msg);
            }
            else
            {
                InternalRemotingServices.RemotingTrace("Content");
                InternalRemotingServices.RemotingTrace("***************** Before Deserialize Headers *****");

                InternalRemotingServices.RemotingTrace("***************** After Deserialize Headers *****");

                InternalRemotingServices.RemotingTrace("***************** Before Deserialize Message *****");

                if (methodRequest == true)
                {
                    MethodCall mc = new MethodCall(h);
                    InternalRemotingServices.RemotingTrace("***************** Before Deserialize Message - as MethodCall *****");
                    fmt.Deserialize(fmtStm, new HeaderHandler(mc.HeaderHandler));
                    ret = mc;
                }
                else
                {
                    IMethodCallMessage mcm = (IMethodCallMessage)msg;
                    MethodResponse mr = new MethodResponse(h, mcm);
                    InternalRemotingServices.RemotingTrace("***************** Before Deserialize Message - as MethodResponse *****");
                    fmt.Deserialize(fmtStm, new HeaderHandler(mr.HeaderHandler));
                    ret = mr;
                }

                InternalRemotingServices.RemotingTrace("***************** After Deserialize Message *****");
            }

            // Workaround to make this method verifiable
            IMessage resMessage = (IMessage) ret;

            InternalRemotingServices.RemotingTrace("CoreChannel::DeserializeMessage OUT");
            CoreChannel.DebugMessage(resMessage);

            return resMessage;
        }
コード例 #11
0
        } // DeserializeSoapRequestMessage


        internal static IMessage DeserializeSoapResponseMessage(
            Stream inputStream, IMessage requestMsg, Header[] h, bool bStrictBinding)
        {
            SoapFormatter fmt = CreateSoapFormatter(false, bStrictBinding);

            IMethodCallMessage mcm = (IMethodCallMessage)requestMsg;
            MethodResponse mr = new MethodResponse(h, mcm);
            fmt.Deserialize(inputStream, new HeaderHandler(mr.HeaderHandler));

            IMessage resMessage = (IMessage)mr;

            return resMessage;
        } // DeserializeSoapResponseMessage
コード例 #12
0
 internal static IMessage DeserializeMessage(string mimeType, Stream xstm, bool methodRequest, IMessage msg, Header[] h)
 {
     Stream serializationStream = null;
     object obj2;
     bool flag = false;
     bool flag2 = true;
     if (string.Compare(mimeType, "application/octet-stream", StringComparison.Ordinal) == 0)
     {
         flag2 = true;
     }
     if (string.Compare(mimeType, "text/xml", StringComparison.Ordinal) == 0)
     {
         flag2 = false;
     }
     if (!flag)
     {
         serializationStream = xstm;
     }
     else
     {
         long position = xstm.Position;
         byte[] bytes = ((MemoryStream) xstm).ToArray();
         xstm.Position = position;
         MemoryStream stream3 = new MemoryStream(Convert.FromBase64String(Encoding.ASCII.GetString(bytes, 0, bytes.Length)));
         serializationStream = stream3;
     }
     IRemotingFormatter formatter = MimeTypeToFormatter(mimeType, false);
     if (flag2)
     {
         obj2 = ((BinaryFormatter) formatter).UnsafeDeserializeMethodResponse(serializationStream, null, (IMethodCallMessage) msg);
     }
     else if (methodRequest)
     {
         MethodCall call = new MethodCall(h);
         formatter.Deserialize(serializationStream, new HeaderHandler(call.HeaderHandler));
         obj2 = call;
     }
     else
     {
         IMethodCallMessage mcm = (IMethodCallMessage) msg;
         MethodResponse response = new MethodResponse(h, mcm);
         formatter.Deserialize(serializationStream, new HeaderHandler(response.HeaderHandler));
         obj2 = response;
     }
     return (IMessage) obj2;
 }
 public virtual IMessage SyncProcessMessage(IMessage reqMsg)
 {
     IMessage message = InternalSink.ValidateMessage(reqMsg);
     if (message != null)
     {
         return message;
     }
     IPrincipal principal = null;
     IMessage message2 = null;
     try
     {
         SmuggledMethodReturnMessage message5;
         IMethodCallMessage message3 = reqMsg as IMethodCallMessage;
         if (message3 != null)
         {
             LogicalCallContext logicalCallContext = message3.LogicalCallContext;
             if (logicalCallContext != null)
             {
                 principal = logicalCallContext.RemovePrincipalIfNotSerializable();
             }
         }
         MemoryStream stream = null;
         SmuggledMethodCallMessage smuggledMcm = SmuggledMethodCallMessage.SmuggleIfPossible(reqMsg);
         if (smuggledMcm == null)
         {
             stream = CrossAppDomainSerializer.SerializeMessage(reqMsg);
         }
         LogicalCallContext callCtx = CallContext.SetLogicalCallContext(null);
         MemoryStream stm = null;
         byte[] buffer = null;
         try
         {
             if (smuggledMcm != null)
             {
                 buffer = this.DoTransitionDispatch(null, smuggledMcm, out message5);
             }
             else
             {
                 buffer = this.DoTransitionDispatch(stream.GetBuffer(), null, out message5);
             }
         }
         finally
         {
             CallContext.SetLogicalCallContext(callCtx);
         }
         if (message5 != null)
         {
             ArrayList deserializedArgs = message5.FixupForNewAppDomain();
             message2 = new MethodResponse((IMethodCallMessage) reqMsg, message5, deserializedArgs);
         }
         else if (buffer != null)
         {
             stm = new MemoryStream(buffer);
             message2 = CrossAppDomainSerializer.DeserializeMessage(stm, reqMsg as IMethodCallMessage);
         }
     }
     catch (Exception exception)
     {
         try
         {
             message2 = new ReturnMessage(exception, reqMsg as IMethodCallMessage);
         }
         catch (Exception)
         {
         }
     }
     if (principal != null)
     {
         IMethodReturnMessage message6 = message2 as IMethodReturnMessage;
         if (message6 != null)
         {
             message6.LogicalCallContext.Principal = principal;
         }
     }
     return message2;
 }
コード例 #14
0
            void ProcessReceive(SocketAsyncEventArgs e)
            {
                if (e.BytesTransferred > 0)
                {
                    if (e.SocketError == SocketError.Success)
                    {
                        totalBuffer = Combine(totalBuffer, e.Buffer);

                        if (e.AcceptSocket.Available == 0)
                        {
                            //.Net Remoting Protocol Parser
                            #region Read Request
                            Console.WriteLine("==== .Net Remoting Protocol Parser ====");
                            //1. Preamble, will be ".NET"
                            Console.WriteLine("Preamble: {0}", Encoding.ASCII.GetString(new byte[] {
                            totalBuffer[0],
                            totalBuffer[1],
                            totalBuffer[2],
                            totalBuffer[3] }));
                            //2. MajorVersion, will be 1
                            Console.WriteLine("MajorVersion: {0}", totalBuffer[4]);
                            //3. MinorVersion, will be 0
                            Console.WriteLine("MinorVersion: {0}", totalBuffer[5]);
                            //4. Operation, will be 5 (request,onewayrequest...)
                            Console.WriteLine("Operation: {0}", (UInt16)(totalBuffer[6] & 0xFF | totalBuffer[7] << 8));
                            //5. TcpContentDelimiter and ContentLength
                            var header = (UInt16)(totalBuffer[8] & 0xFF | totalBuffer[9] << 8);
                            if (header == 1)
                                Console.WriteLine("Chunked: {0}", true);
                            else
                                Console.WriteLine("ContentLength: {0}"
                                    , (int)((totalBuffer[10] & 0xFF)
                                    | totalBuffer[11] << 8
                                    | totalBuffer[12] << 16
                                    | totalBuffer[13] << 24));

                            #region 6. ReadHeaders ITransportHeaders
                            Console.WriteLine("---- ITransportHeaders ----");
                            var index = header == 1 ? 9 : 13;
                            var headerType = ReadUInt16(ref index);
                            while (headerType != TcpHeaders.EndOfHeaders)
                            {
                                if (headerType == TcpHeaders.Custom)
                                {
                                    Console.WriteLine("{0}: {1}", ReadCountedString(ref index), ReadCountedString(ref index));
                                }
                                else if (headerType == TcpHeaders.RequestUri)
                                {
                                    Console.WriteLine("RequestUri-Format: {0}", ReadByte(ref index));
                                    Console.WriteLine("RequestUri: {0}", ReadCountedString(ref index));
                                }
                                else if (headerType == TcpHeaders.StatusCode)
                                {
                                    Console.WriteLine("StatusCode-Format: {0}", ReadByte(ref index));
                                    var code = ReadUInt16(ref index);
                                    Console.WriteLine("StatusCode: {0}", code);
                                    //if (code != 0) error = true;
                                }
                                else if (headerType == TcpHeaders.StatusPhrase)
                                {
                                    Console.WriteLine("StatusPhrase-Format: {0}", ReadByte(ref index));
                                    Console.WriteLine("StatusPhrase: {0}", ReadCountedString(ref index));
                                }
                                else if (headerType == TcpHeaders.ContentType)
                                {
                                    Console.WriteLine("ContentType-Format: {0}", ReadByte(ref index));
                                    Console.WriteLine("ContentType: {0}", ReadCountedString(ref index));
                                }
                                else
                                {
                                    var headerFormat = (byte)ReadByte(ref index);

                                    switch (headerFormat)
                                    {
                                        case TcpHeaderFormat.Void: break;
                                        case TcpHeaderFormat.CountedString: ReadCountedString(ref index); break;
                                        case TcpHeaderFormat.Byte: ReadByte(ref index); break;
                                        case TcpHeaderFormat.UInt16: ReadUInt16(ref index); break;
                                        case TcpHeaderFormat.Int32: ReadInt32(ref index); break;
                                        default:
                                            throw new RemotingException("Remoting_Tcp_UnknownHeaderType");
                                    }
                                }

                                headerType = ReadUInt16(ref index);
                            }
                            #endregion

                            //7. RequestStream/Message
                            var requestStream = new byte[totalBuffer.Length - index - 1];
                            Buffer.BlockCopy(totalBuffer, index + 1, requestStream, 0, totalBuffer.Length - index - 1);
                            //using BinaryFormatterSink default
                            var requestMessage = BinaryFormatterHelper.DeserializeObject(requestStream) as MethodCall;
                            DumpHelper.DumpMessage(requestMessage);
                            #endregion

                            buffers = new StringBuilder();
                            totalBuffer = new byte[0];

                            #region Write Response

                            //http://labs.developerfusion.co.uk/SourceViewer/browse.aspx?assembly=SSCLI&namespace=System.Runtime.Remoting
                            //else if (name.Equals("__Return"))
                            var responeMessage = new MethodResponse(
                                //just return args[0]
                                new Header[] { new Header("__Return", requestMessage.Args[0]) }
                                , requestMessage);

                            //responeMessage.ReturnValue//can not set
                            var responseStream = BinaryFormatterHelper.SerializeObject(responeMessage);
                            //1.Preamble
                            var preamble = Encoding.ASCII.GetBytes(".NET");
                            foreach (var b in preamble)
                                WriteByte(b);
                            //2.MajorVersion
                            WriteByte((byte)1);
                            //3.MinorVersion
                            WriteByte((byte)0);
                            //4.Operation
                            WriteUInt16(TcpOperations.Reply);
                            //5.TcpContentDelimiter and ContentLength
                            WriteUInt16(0);
                            WriteInt32(responseStream.Length);
                            //6.Headers
                            WriteUInt16(TcpHeaders.EndOfHeaders);
                            //7.ResponseStream/Message
                            foreach (var b in responseStream)
                                WriteByte(b);
                            #endregion

                            e.SetBuffer(totalBuffer, 0, totalBuffer.Length);
                            if (!e.AcceptSocket.SendAsync(e))
                            {
                                this.ProcessSend(e);
                            }
                        }
                        else if (!e.AcceptSocket.ReceiveAsync(e))
                        {
                            this.ProcessReceive(e);
                        }
                    }
                    else
                    {
                        //this.ProcessError(e);
                    }
                }
                else
                {
                    //this.CloseClientSocket(e);
                }
            }