[英]Async Tcp Server cannot receive data
I am currently tyring to create a Multi threading and async tcp server that implements the Tcpl listener 我目前正在尝试创建实现Tcpl侦听器的多线程和异步tcp服务器
Current the server is working as intended as i am able to send data to the server an transmit data to the client with out any problems 当前服务器正在按预期工作,因为我能够将数据发送到服务器并将数据发送到客户端而没有任何问题
However after i have sent data to the server and then sent data back to the client, when the client sends data back to the server again the server is unabe to pick up the data 但是,在我将数据发送到服务器然后又将数据发送回客户端之后,当客户端再次将数据发送回服务器时,服务器将无法取回数据
I have tried for days to find an answer to this problem however with no luck 我已经尝试了好几天才能找到这个问题的答案,但是没有运气
Here is the code that i am currently using in the server: 这是我当前在服务器中使用的代码:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Net;
using System.Net.Sockets;
using System.Threading;
using System.Windows.Forms;
using System.IO;
namespace MyTcpAsyncClass
{
public class StateObject
{
public TcpClient MyTcpClient = null;
public NetworkStream MyNetworkStream = null;
public const int MyBufferSize = 1024;
public byte[] MyBuffer = new byte[MyBufferSize];
public string RequestString = "";
public StringBuilder MyStringBuilder = new StringBuilder();
char[] RequestChars; // Char array of Request
const char STX = (char)0x02; // Start Character
const char FTX = (char)0x03; // Finish Character
public void Dispose()
{
try
{
MyTcpClient.Close();
MyNetworkStream.Close();
MyNetworkStream.Dispose();
}
catch (Exception ex)
{
MessageBox.Show("Message:\n" + ex.Message + "\n\nStacktrace:\n" + ex.StackTrace);
}
}
}
public static class AsyncServerFunctions
{
private static int mPort = 0;
private static ManualResetEvent MyManualResetEvent = new ManualResetEvent(false);
public static void StartListening()
{
//Catch to Tcp Client Connection
try
{
//Get the database connection
//MyReaderWriterLockSlim.EnterReadLock();
LoadSettings();
//MyReaderWriterLockSlim.ExitReadLock();
TcpListener MyTcpListener = new TcpListener(IPAddress.Any, mPort);
MyTcpListener.Start();
while (true)
{
//Set the event to nonsignaled state
MyManualResetEvent.Reset();
//Start an asynchronous TcpListener to listen for a connection
MyTcpListener.BeginAcceptTcpClient(AcceptTcpClientCallback, MyTcpListener);
//Wait until a connection is made before continuing
MyManualResetEvent.WaitOne();
}
MyTcpListener.Stop();
}
catch (Exception ex)
{
AddErrorLog(ex.Message, ex.StackTrace);
}
}
private static void AcceptTcpClientCallback(IAsyncResult result)
{
try
{
//BeginAcceptTcpClientCallback
//Signal the main thread to continue
MyManualResetEvent.Set();
//Get the TcpClientNetworkStream:
TcpListener MyTcpListener = (TcpListener)result.AsyncState;
//Finish Async Get Client Process
TcpClient MyTcpClient = MyTcpListener.EndAcceptTcpClient(result);
StateObject MyStateObject = new StateObject();
MyStateObject.MyTcpClient = MyTcpClient;
MyStateObject.MyNetworkStream = MyTcpClient.GetStream();
//Begin Async read from the NetworkStream
MyStateObject.MyNetworkStream.BeginRead(MyStateObject.MyBuffer, 0, StateObject.MyBufferSize, new AsyncCallback(BeginReadCallback), MyStateObject);
}
catch (Exception ex)
{
AddErrorLog(ex.Message, ex.StackTrace);
}
}
private static void BeginReadCallback(IAsyncResult result)
{
StateObject MyStateObject = (StateObject)result.AsyncState;
NetworkStream MyNetworkStream = MyStateObject.MyNetworkStream;
string MyRequestString = "";
try
{
//Get Request Data here
if (MyStateObject.MyBuffer.Length > 0)
{
//Store the data recived
MyStateObject.MyStringBuilder.Clear();
MyStateObject.MyStringBuilder.Append(Encoding.ASCII.GetString(MyStateObject.MyBuffer));
//Get the stored Request string
MyRequestString = MyStateObject.MyStringBuilder.ToString();
//Record the string recived
DatabaseFunctions.AddMessageLog("String Recived (BeginReadCallback): " + MyRequestString);
//Remove the first and last character
MyRequestString = CleanString(MyRequestString);
//Record the Request String
DatabaseFunctions.AddMessageLog("Request String Recived:" + MyRequestString);
//Get the Message Identifier
string MessageIdentifier = "";
MessageIdentifier = MyRequestString.Substring(0, 2);
switch (MessageIdentifier)
{
case "value":
SendResponse(MyStateObject, StartUp(MessageIdentifier, MyRequestString));
SendResponse(MyStateObject, SendTransactionStart(MessageIdentifier, MyAmount));
GetResponse(MyStateObject);
break;
default:
//***Default Case***
SendResponse(MyStateObject, DefaultCase(MyRequestString));
break;
}
//Dispose of the connection
MyStateObject.Dispose();
}
}
catch (Exception ex)
{
AddErrorLog(ex.Message, ex.StackTrace);
try
{
MyStateObject.Dispose();
}
catch
{
AddErrorLog(ex.Message, ex.StackTrace);
}
}
}
private static void SendResponse(StateObject pMyStateObject, string pResponseString)
{
try
{
//Send a response to the client
//Get bytes from string sent
byte[] MyResponseBytes = Encoding.ASCII.GetBytes(pResponseString);
//Get the network stream
NetworkStream MyNetworkStream = pMyStateObject.MyNetworkStream;
//Call SendResponseCallback
MyNetworkStream.BeginWrite(MyResponseBytes, 0, MyResponseBytes.Length, new AsyncCallback(SendResponseCallback), pMyStateObject);
}
catch (Exception ex)
{
AddErrorLog(ex.Message, ex.StackTrace);
}
}
private static void GetResponse(StateObject pStateObject)
{
//This will run a new AsyncCallback To get the response from the client
NetworkStream MyNetworkStream = pStateObject.MyNetworkStream;
pStateObject.MyBuffer = new byte[1024];
MyNetworkStream.BeginRead(pStateObject.MyBuffer, 0, pStateObject.MyBuffer.Length, new AsyncCallback(BeginReadCallback), pStateObject);
}
private static void SendResponseCallback(IAsyncResult result)
{
try
{
//End the send procedure
StateObject MyStateObject = (StateObject)result.AsyncState;
NetworkStream MyNetworkStream = MyStateObject.MyNetworkStream;
MyNetworkStream.Flush();
}
catch (Exception ex)
{
AddErrorLog(ex.Message, ex.StackTrace)
}
}
private static void ShowExceptionMessage(string pMessage, string pStacktrace)
{
MessageBox.Show("Message:\n" + pMessage + "\n\nStacktrace:\n" + pStacktrace);
}
private static void AddErrorLog(string pMessage, string pStackTrace)
{
DatabaseFunctions.AddMessageLog("Message:" + pMessage + "; Stacktrace:" + pStackTrace);
}
}
}
Thanks All 谢谢大家
You should call BeginAcceptTcpClient
in AcceptTcpClientCallback
also. 您还应该在AcceptTcpClientCallback
调用BeginAcceptTcpClient
。 You don't accept any new connection after the first one. 在第一个连接之后,您不接受任何新连接。
在BeginReadCallback
函数中,释放用于调用BeginRead
的对象,然后尝试运行代码而不使用dispose函数,而仅在切换条件下调用GetRespone
函数,请尝试在BeginReadCallback
函数中调用BeginRead
。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.