C# iocp通讯客户端只能发送数据,无法接收服务端发送的数据
2013-07-30 11:07
696 查看
using System; using System.IO; using System.ComponentModel; using System.Collections; using System.Diagnostics; using System.Net; using System.Net.Sockets; using System.Threading; using System.Text; namespace IOCP { /// /// MyTcpIpClient 提供在Net TCP_IP 协议上基于消息的服务端 /// public class MyTcpIpServer : System.ComponentModel.Component { private int bufferSize = 2048; private string tcpIpServerIP = ""; private int tcpIpServerPort = 8808; private Socket listener = null; private ManualResetEvent allDone = new ManualResetEvent(false); private ManualResetEvent sendDone = new ManualResetEvent(false); private Thread thread = null; private void StartListening() { try { listener = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); IPAddress ipAddress; if (tcpIpServerIP.Trim() == "") { ipAddress = IPAddress.Any; } else { ipAddress = IPAddress.Parse(tcpIpServerIP); } IPEndPoint localEndPoint = new IPEndPoint(ipAddress, tcpIpServerPort); listener.Bind(localEndPoint); listener.Listen(100000); while (true) { allDone.Reset(); listener.BeginAccept(new AsyncCallback(AcceptCallback), listener); allDone.WaitOne(); } } catch (Exception e) { OnErrorServerEvent(new ErrorServerEventArgs(e, listener)); } } private void ReadCallback(IAsyncResult ar) { Socket handler = null; try { lock (ar) { StateObject state = (StateObject)ar.AsyncState; handler = state.workSocket; int bytesRead = handler.EndReceive(ar); if (bytesRead > 0) { Console.WriteLine(Encoding.UTF8.GetString(state.buffer, 0, bytesRead)); byte[] arrb = Encoding.UTF8.GetBytes("ffffffffffffffffffffff"); Stream sr = new MemoryStream(arrb); //Send(handler, sr); int ReadPiont = 0; while (ReadPiont < bytesRead) { if (state.Cortrol == 0 && ReadPiont < bytesRead) { long bi1 = state.buffer[ReadPiont]; bi1 = (bi1 << 24) & 0xff000000; state.packSize = bi1; ReadPiont++; state.Cortrol = 1; } if (state.Cortrol == 1 && ReadPiont < bytesRead) { long bi1 = state.buffer[ReadPiont]; bi1 = (bi1 << 16) & 0x00ff0000; state.packSize = state.packSize + bi1; ReadPiont++; state.Cortrol = 2; } if (state.Cortrol == 2 && ReadPiont < bytesRead) { long bi1 = state.buffer[ReadPiont]; bi1 = (bi1 << 8) & 0x0000ff00; state.packSize = state.packSize + bi1; ReadPiont++; state.Cortrol = 3; } if (state.Cortrol == 3 && ReadPiont < bytesRead) { long bi1 = state.buffer[ReadPiont]; bi1 = bi1 & 0xff; state.packSize = state.packSize + bi1 - 4; ReadPiont++; state.Cortrol = 4; } if (state.Cortrol == 4 && ReadPiont < bytesRead) { long bi1 = state.buffer[ReadPiont]; bi1 = (bi1 << 24) & 0xff000000; state.residualSize = bi1; ReadPiont++; state.Cortrol = 5; state.packSize -= 1; } if (state.Cortrol == 5 && ReadPiont < bytesRead) { long bi1 = state.buffer[ReadPiont]; bi1 = (bi1 << 16) & 0x00ff0000; state.residualSize = state.residualSize + bi1; ReadPiont++; state.Cortrol = 6; state.packSize -= 1; } if (state.Cortrol == 6 && ReadPiont < bytesRead) { long bi1 = state.buffer[ReadPiont]; bi1 = (bi1 << 8) & 0x0000ff00; state.residualSize = state.residualSize + bi1; ReadPiont++; state.Cortrol = 7; state.packSize -= 1; } if (state.Cortrol == 7 && ReadPiont < bytesRead) { long bi1 = state.buffer[ReadPiont]; bi1 = bi1 & 0xff; state.residualSize = state.residualSize + bi1; state.Datastream.SetLength(0); state.Datastream.Position = 0; ReadPiont++; state.Cortrol = 8; state.packSize -= 1; } if (state.Cortrol == 8 && ReadPiont < bytesRead) { int bi1 = bytesRead - ReadPiont; int bi2 = (int)(state.residualSize - state.Datastream.Length); if (bi1 >= bi2) { state.Datastream.Write(state.buffer, ReadPiont, bi2); ReadPiont += bi2; OnInceptServerEvent(new InceptServerEventArgs(state.Datastream, state.workSocket, this)); state.Cortrol = 9; state.packSize -= bi2; } else { state.Datastream.Write(state.buffer, ReadPiont, bi1); ReadPiont += bi1; state.packSize -= bi1; } } if (state.Cortrol == 9 && ReadPiont < bytesRead) { int bi1 = bytesRead - ReadPiont; if (bi1 != 0) { state.packSize = state.packSize - bi1; ReadPiont += bi1; } else { state.Cortrol = 0; ReadPiont += (int)state.packSize; } } } if (handler.Connected == true) { handler.BeginReceive(state.buffer, 0, bufferSize, 0, new AsyncCallback(ReadCallback), state); } } else { handler.Shutdown(SocketShutdown.Both); handler.Close(); //throw(new Exception("读入的数据小于1bit")); } } } catch (Exception e) { OnErrorServerEvent(new ErrorServerEventArgs(e, handler)); } } private void SendCallback(IAsyncResult ar) { Socket client = (Socket)ar.AsyncState; try { int bytesSent = client.EndSend(ar); } catch (Exception e) { OnErrorServerEvent(new ErrorServerEventArgs(e, client)); } finally { sendDone.Set(); } } private void AcceptCallback(IAsyncResult ar) { Socket handler = null; try { Socket listener = (Socket)ar.AsyncState; handler = listener.EndAccept(ar); StateObject state = new StateObject(bufferSize, handler); state.workSocket = handler; handler.BeginReceive(state.buffer, 0, bufferSize, 0, new AsyncCallback(ReadCallback), state); } catch (Exception e) { OnErrorServerEvent(new ErrorServerEventArgs(e, handler)); } finally { allDone.Set(); } } /// /// 析构 /// /// 不知道 protected override void Dispose(bool disposing) { Abort(); } /// /// 引发接收事件 /// /// 数据 protected virtual void OnInceptServerEvent(InceptServerEventArgs e) { if (InceptServer != null) { InceptServer(this, e); } } /// /// 引发错误事件 /// /// 数据 protected virtual void OnErrorServerEvent(ErrorServerEventArgs e) { if (ErrorServer != null) { ErrorServer(this, e); } } /// /// 开始监听访问 /// public void Listening() { //StartListening(); thread = new Thread(new ThreadStart(StartListening)); thread.Name = "MyTcpIpServer.Listening"; thread.Start(); } /// /// 异常中止服务 /// public void Abort() { if (thread != null) { thread.Abort(); listener.Close(); } } /// ///构造 /// /// 父控件 public MyTcpIpServer(System.ComponentModel.IContainer container) { container.Add(this); InitializeComponent(); // // TODO: 在 InitializeComponent 调用后添加任何构造函数代码 // } /// /// 构造 /// public MyTcpIpServer() { InitializeComponent(); // // TODO: 在 InitializeComponent 调用后添加任何构造函数代码 // } #region Component Designer generated code /// /// 设计器支持所需的方法 - 不要使用代码编辑器修改 /// 此方法的内容。 /// private void InitializeComponent() { } #endregion /// /// 要连接的服务器IP地址 /// public string TcpIpServerIP { get { return tcpIpServerIP; } set { tcpIpServerIP = value; } } /// /// 要连接的服务器所使用的端口 /// public int TcpIpServerPort { get { return tcpIpServerPort; } set { tcpIpServerPort = value; } } /// /// 缓冲器大小 /// public int BufferSize { get { return bufferSize; } set { bufferSize = value; } } /// /// 连接的活动状态 /// public bool Activ { get { return listener.Connected; } //set //{ // activ=value; //} } /// /// 发送一个流数据 /// public void Send(Socket ClientSocket, Stream Astream) { try { if (ClientSocket.Connected == false) { throw (new Exception("没有连接客户端不可以发送信息!")); } Astream.Position = 0; byte[] byteData = new byte[bufferSize]; int bi1 = (int)((Astream.Length + 8) / bufferSize); int bi2 = (int)Astream.Length; if (((Astream.Length + 8) % bufferSize) > 0) { bi1 = bi1 + 1; } bi1 = bi1 * bufferSize; byteData[0] = System.Convert.ToByte(bi1 >> 24); byteData[1] = System.Convert.ToByte((bi1 & 0x00ff0000) >> 16); byteData[2] = System.Convert.ToByte((bi1 & 0x0000ff00) >> 8); byteData[3] = System.Convert.ToByte((bi1 & 0x000000ff)); byteData[4] = System.Convert.ToByte(bi2 >> 24); byteData[5] = System.Convert.ToByte((bi2 & 0x00ff0000) >> 16); byteData[6] = System.Convert.ToByte((bi2 & 0x0000ff00) >> 8); byteData[7] = System.Convert.ToByte((bi2 & 0x000000ff)); int n = Astream.Read(byteData, 8, byteData.Length - 8); while (n > 0) { ClientSocket.BeginSend(byteData, 0, byteData.Length, 0, new AsyncCallback(SendCallback), ClientSocket); sendDone.WaitOne(); byteData = new byte[bufferSize]; n = Astream.Read(byteData, 0, byteData.Length); } } catch (Exception e) { OnErrorServerEvent(new ErrorServerEventArgs(e, ClientSocket)); } } /// /// 接收到数据事件 /// public event InceptServerEvent InceptServer; /// /// 发生错误事件 /// public event ErrorServerEvent ErrorServer; } /// /// 状态对象 /// public class StateObject { /// /// 构造 /// /// 缓存 /// 工作的插座 public StateObject(int bufferSize, Socket WorkSocket) { buffer = new byte[bufferSize]; workSocket = WorkSocket; } /// /// 缓存 /// public byte[] buffer = null; /// /// 工作插座 /// public Socket workSocket = null; /// /// 数据流 /// public Stream Datastream = new MemoryStream(); /// /// 剩余大小 /// public long residualSize = 0; /// /// 数据包大小 /// public long packSize = 0; /// /// 计数器 /// public int Cortrol = 0; } /// /// 接收事件 /// public class InceptServerEventArgs : EventArgs { private readonly Stream datastream; private readonly Socket serverSocket; private readonly MyTcpIpServer tcpIpServer; /// /// 构造 /// /// 数据 /// 工作插座 /// 提供服务的TCP/IP对象 public InceptServerEventArgs(Stream Astream, Socket ServerSocket, MyTcpIpServer TcpIpServer) { datastream = Astream; serverSocket = ServerSocket; tcpIpServer = TcpIpServer; } /// /// 数据 /// public Stream Astream { get { return datastream; } } /// /// 工作插座 /// public Socket ServerSocket { get { return serverSocket; } } /// /// 提供TCP/IP服务的服务器对象. /// public MyTcpIpServer TcpIpServer { get { return tcpIpServer; } } } /// /// 接收数据委托 /// public delegate void InceptServerEvent(object sender, InceptServerEventArgs e); /// /// 错误事件委托 /// public class ErrorServerEventArgs : EventArgs { private readonly Exception error; private readonly Socket serverSocket; /// /// 构造 /// /// 数据 /// 问题插座 public ErrorServerEventArgs(Exception Error, Socket ServerSocket) { error = Error; serverSocket = ServerSocket; } /// /// 数据 /// public Exception Error { get { return error; } } /// /// 问题插座 /// public Socket ServerSocket { get { return serverSocket; } } } /// ///错误事件委托 /// public delegate void ErrorServerEvent(object sender, ErrorServerEventArgs e); }
客户端代码:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Net.Sockets;
using System.Net;
using System.Threading;
namespace ClientSocket
{
class Program
{
//创建一个数据缓冲区
private static byte[] m_DataBuffer = new byte[2048];
static void Main(string[] args)
{
IPHostEntry ipHost = Dns.Resolve(Dns.GetHostName());
IPAddress ip = ipHost.AddressList[0];
Socket client = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
try
{
client.Connect(new IPEndPoint(ip, 8088));
Console.WriteLine("连接server成功!");
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
return;
}
//client接收数据
// int receiveLength = 0;
// try
// {
// receiveLength = client.Receive(m_DataBuffer);
// }
// catch (System.Exception ex)
// {
// string ss= ex.Message;
// }
//Console.WriteLine("接受server消息"+ Encoding.UTF8.GetString(m_DataBuffer, 0, receiveLength));
//client发送数据
int receiveLength = 0;
for (int i = 0; i < 1000; i++)
{
try
{
//* 、、*/ Thread.Sleep(1000);
string msg = "Server你好!"+DateTime.Now.ToString();
client.Send(Encoding.UTF8.GetBytes(msg));
Console.WriteLine("发送的消息为:{0}", msg);
try
{
m_DataBuffer = new byte[2048];
receiveLength = client.Receive(m_DataBuffer);
}
catch (System.Exception ex)
{
string ss = ex.Message;
}
Console.WriteLine("接受的消息:" + Encoding.UTF8.GetString(m_DataBuffer, 0, receiveLength));
}
catch
{
client.Shutdown(SocketShutdown.Both);
client.Close();
break;
}
}
Console.WriteLine("发送完毕!");
//发送完消息后关闭连接
client.Shutdown(SocketShutdown.Both);
client.Close();
Console.Read();
}
}
}
相关文章推荐
- java netty 服务端向客户端发送16进制数据,客户端无法接收-已解决
- Java Socket 服务端发送数据 客户端接收数据
- 模仿客户端通过http协议向服务端发送和接收数据
- httpmime-4.1.3.jar和httpmime-4.3.6.jar 发送的http请求有差异,导致服务端无法接收到数据。
- (四)XML基础(客户端和服务端发送与接收xml数据)
- TCP与UDP的异同(服务端接收数据,客户端发送数据)
- TCP与UDP的异同(服务端接收数据,客户端发送数据)
- TCP与UDP的异同(服务端接收数据,客户端发送数据)
- socket客户端数据发送的数据服务端接收不到
- 客户端POST发送json数据给服务端,客户端端接收服务器端json数据响应
- 关于servlet服务端接收客户端发送的List<?>数据的问题
- TCP与UDP的异同(服务端接收数据,客户端发送数据)
- 一个简单的socket服务端和客户端程序:客户端发送数据给服务端,服务端接收到数据后再给客户端发送数据
- java 基于tcp客户端服务端发送接收数据
- 数据报实现简单的客户端发送数据,服务端接收数据
- vue 集成 axios 发送post请求 payload导致后台无法接收到数据问题
- ajax之xml数据的服务器端发送和客户端接收。
- socket服务器发送大数据,客户端循环接收
- aJax提交——服务端不能用request存储数据,session存数据客户端可以接收到
- 客户端读取本地文件的数据,发送到服务器,服务器接收并存储到文件中