C# 的TCP Socket (异步方式)
2023-09-27 14:23:42 时间
C# TCP socket发送大数据包时,接收端和发送端数据不一致 服务端接收Receive不完全
服务器端:
public static ManualResetEvent allDone = new ManualResetEvent(false); IPEndPoint localEndPoint = new IPEndPoint(IPAddress.Parse("127.0.0.1"), port); Socket listener = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); listener.Bind(localEndPoint); listener.Listen(30); while (true) { allDone.Reset(); listener.BeginAccept(new AsyncCallback(AcceptCallback), listener); allDone.WaitOne(); }
public static void AcceptCallback(IAsyncResult ar) { try { if (IsListening) { allDone.Set(); Socket listener = (Socket)ar.AsyncState; Socket handler = listener.EndAccept(ar); StateObject state = new StateObject(); state.workSocket = handler; handler.BeginReceive(state.headbuffer, 0, StateObject.HeadBufferSize, 0, new AsyncCallback(ReceiveHead), state); } } catch (System.Exception ex) { log.ErrorFormat("AcceptCallback异常,原因:{0}", ex.Message); } } private static void ReceiveHead(IAsyncResult ar) { try { StateObject state = (StateObject)ar.AsyncState; Socket handler = state.workSocket; int bytesRead = handler.EndReceive(ar); uint length = ByteTouint(state.headbuffer, 3, 4); state.length = (int)length - state.headbuffer.Length; state.bodybuffer = new byte[length - state.headbuffer.Length]; handler.BeginReceive(state.bodybuffer, 0, state.bodybuffer.Length, 0, new AsyncCallback(ReadCallback), state); } catch (System.Exception ex) { log.ErrorFormat("ReceiveHead异常,原因:{0}", ex.Message + ex.StackTrace); } }
public static void ReadCallback(IAsyncResult ar) { StateObject state = (StateObject)ar.AsyncState; Socket handler = state.workSocket; int bytesRead = handler.EndReceive(ar); //接收的字节在state.bodybuffer里,下面开始处理 }
已知接收长度的话可以把ReceiveHead函数去掉,直接进入ReadCallback里。
加入ReceiveHead是因为协议一般在开头几个固定的字节里有后面数据包的长度,所以先接收头,再根据解析出的数据包长度接收后面的。
StateObject定义如下,可以不要headbuffer HeadBufferSize
public class StateObject { public Socket workSocket = null; public const int HeadBufferSize = 7; public byte[] headbuffer = new byte[HeadBufferSize]; public byte[] bodybuffer; public int length; }
客户端发送数据 C# 的TCP Socket (同步方式)
相关文章
- C#中直接调用halcon的.hdev文件的函数【附源码】
- C#---Winform的数据绑定和窗体操作
- C#实现微信AES-128-CBC加密数据的解密
- C# 的TCP Socket (同步方式)
- UDP 网络通信 C#
- C#图像处理-OpenCVSharp教程(三十八) OpenCVSharp简单人脸识别实例
- c#读写配置文件
- .NET(C#) Linq Skip和SkipWhile的使用
- Redis 小白指南(一)- 简介、安装、GUI 和 C# 驱动介绍
- [C#] C# 知识回顾 - 表达式树 Expression Trees
- C#中使用7Z进行压缩解压
- 2019-8-31-C#-获取进程退出代码
- C# 从 short 转 byte 方法