NetServer是一个网络通信模块,基于CompletionPort实现,适用于服务器端。它在VC下实现,可以直接在VC环境下使用,也可以通过DllImport在.Net环境下使用。
它实现的功能如下:
Code
1 /**//// <summary>
2 /// 网络通讯模块的服务器端实现,基于CompletionPort、TCP。
3 /// </summary>
4 public class NetServer
5 {
6 /**//// <summary>
7 /// 当客户端连上的响应委托
8 /// </summary>
9 /// <param name="sock">用于与客户端连接的服务器端套接字</param>
10 public delegate void OnAccepted(int sock);
11
12 /**//// <summary>
13 /// 当接收到来自客户端数据时的响应委托
14 /// </summary>
15 /// <param name="sock">用于与客户端连接的服务器端套接字</param>
16 /// <param name="pData">接收到的数据的起始字节</param>
17 /// <param name="len">接收的数据长度</param>
18 public delegate void OnDataReceived(int sock, IntPtr pData, int len);
19
20 /**//// <summary>
21 /// 当数据发送完毕时的响应委托
22 /// </summary>
23 /// <param name="sock">用于与客户端连接的服务器端套接字</param>
24 /// <param name="len">发送的数据长度</param>
25 public delegate void OnDataSent(int sock, int len);
26
27 /**//// <summary>
28 /// 当客户端断开连接时的响应委托
29 /// </summary>
30 /// <param name="sock">用于与客户端连接的服务器端套接字</param>
31 public delegate void OnDisconnected(int sock);
32
33 /**//// <summary>
34 /// 设置接收缓冲区大小,默认为1024字节
35 /// </summary>
36 /// <param name="bufferSize">缓冲区大小</param>
37 [DllImport("nc.dll")]
38 public static extern void SetDataBufferSize(int bufferSize);
39
40 /**//// <summary>
41 /// 设置在CompletionPort上工作的线程数,默认为 2×CPU个数 + 2
42 /// </summary>
43 /// <param name="count">线程数</param>
44 [DllImport("nc.dll")]
45 public static extern void SetCompletionThreadCount(int count);
46
47 /**//// <summary>
48 /// 设置监听端口
49 /// </summary>
50 /// <param name="port">监听端口</param>
51 [DllImport("nc.dll")]
52 public static extern void SetListenPort(int port);
53
54 /**//// <summary>
55 /// 设置等待队列的长度,默认为10
56 /// </summary>
57 /// <param name="backlog">等待队列长度</param>
58 [DllImport("nc.dll")]
59 public static extern void SetBacklog(int backlog);
60
61 /**//// <summary>
62 /// 获取服务端状态
63 /// </summary>
64 /// <returns>返回服务器端状态,0表示未启动,1表示启动</returns>
65 [DllImport("nc.dll")]
66 public static extern int IsStartUp();
67
68 /**//// <summary>
69 /// 服务器端启动
70 /// </summary>
71 /// <returns>返回启动结果,0表示启动失败,1表示启动成功</returns>
72 [DllImport("nc.dll")]
73 public static extern int StartUp();
74
75 /**//// <summary>
76 /// 服务器端停止
77 /// </summary>
78 [DllImport("nc.dll")]
79 public static extern void Stop();
80
81 /**//// <summary>
82 /// 向指定的套接字投递一个接收指令,服务器端将异步接收
83 /// </summary>
84 /// <param name="sock">指定的套接字</param>
85 [DllImport("nc.dll")]
86 public static extern void Receive(int sock);
87
88 /**//// <summary>
89 /// 向指定的套接字投递一个发送指令,服务器端将异步发送
90 /// </summary>
91 /// <param name="sock">指定的套接字</param>
92 /// <param name="buf">待发送的数据</param>
93 /// <param name="buflen">发送的数据长度,= buf.Length</param>
94 [DllImport("nc.dll")]
95 public static extern void Send(int sock, byte[] buf, int buflen);
96
97 /**//// <summary>
98 /// 与和指定套接字连接的客户端断开连接
99 /// </summary>
100 /// <param name="sock">指定的套接字</param>
101 [DllImport("nc.dll")]
102 public static extern void ShutDown(int sock);
103
104 /**//// <summary>
105 /// 设置最大连接数,默认1000
106 /// </summary>
107 /// <param name="maxConnection">连接数</param>
108 [DllImport("nc.dll")]
109 public static extern void SetMaxConnection(int maxConnection);
110
111 /**//// <summary>
112 /// 设置当服务器端接收到连接时的自定义响应
113 /// </summary>
114 /// <param name="cbf">委托实例,请用成员变量保存,否则被GC后会报异常</param>
115 [DllImport("nc.dll")]
116 public static extern void SetAcceptConnectFP(OnAccepted cbf);
117
118 /**//// <summary>
119 /// 设置当服务器端接收到数据时的自定义响应
120 /// </summary>
121 /// <param name="cbf">委托实例,请用成员变量保存,否则被GC后会报异常</param>
122 [DllImport("nc.dll")]
123 public static extern void SetDataReceivedFP(OnDataReceived cbf);
124
125 /**//// <summary>
126 /// 设置当服务器端数据发送完毕时的自定义响应
127 /// </summary>
128 /// <param name="cbf">委托实例,请用成员变量保存,否则被GC后会报异常</param>
129 [DllImport("nc.dll")]
130 public static extern void SetDataSentFP(OnDataSent cbf);
131
132 /**//// <summary>
133 /// 设置当客户端断开连接时的自定义响应
134 /// </summary>
135 /// <param name="cbf">委托实例,请用成员变量保存,否则被GC后会报异常</param>
136 [DllImport("nc.dll")]
137 public static extern void SetHandleDisconnectFP(OnDisconnected cbf);
138 }
1 /**//// <summary>
2 /// 网络通讯模块的服务器端实现,基于CompletionPort、TCP。
3 /// </summary>
4 public class NetServer
5 {
6 /**//// <summary>
7 /// 当客户端连上的响应委托
8 /// </summary>
9 /// <param name="sock">用于与客户端连接的服务器端套接字</param>
10 public delegate void OnAccepted(int sock);
11
12 /**//// <summary>
13 /// 当接收到来自客户端数据时的响应委托
14 /// </summary>
15 /// <param name="sock">用于与客户端连接的服务器端套接字</param>
16 /// <param name="pData">接收到的数据的起始字节</param>
17 /// <param name="len">接收的数据长度</param>
18 public delegate void OnDataReceived(int sock, IntPtr pData, int len);
19
20 /**//// <summary>
21 /// 当数据发送完毕时的响应委托
22 /// </summary>
23 /// <param name="sock">用于与客户端连接的服务器端套接字</param>
24 /// <param name="len">发送的数据长度</param>
25 public delegate void OnDataSent(int sock, int len);
26
27 /**//// <summary>
28 /// 当客户端断开连接时的响应委托
29 /// </summary>
30 /// <param name="sock">用于与客户端连接的服务器端套接字</param>
31 public delegate void OnDisconnected(int sock);
32
33 /**//// <summary>
34 /// 设置接收缓冲区大小,默认为1024字节
35 /// </summary>
36 /// <param name="bufferSize">缓冲区大小</param>
37 [DllImport("nc.dll")]
38 public static extern void SetDataBufferSize(int bufferSize);
39
40 /**//// <summary>
41 /// 设置在CompletionPort上工作的线程数,默认为 2×CPU个数 + 2
42 /// </summary>
43 /// <param name="count">线程数</param>
44 [DllImport("nc.dll")]
45 public static extern void SetCompletionThreadCount(int count);
46
47 /**//// <summary>
48 /// 设置监听端口
49 /// </summary>
50 /// <param name="port">监听端口</param>
51 [DllImport("nc.dll")]
52 public static extern void SetListenPort(int port);
53
54 /**//// <summary>
55 /// 设置等待队列的长度,默认为10
56 /// </summary>
57 /// <param name="backlog">等待队列长度</param>
58 [DllImport("nc.dll")]
59 public static extern void SetBacklog(int backlog);
60
61 /**//// <summary>
62 /// 获取服务端状态
63 /// </summary>
64 /// <returns>返回服务器端状态,0表示未启动,1表示启动</returns>
65 [DllImport("nc.dll")]
66 public static extern int IsStartUp();
67
68 /**//// <summary>
69 /// 服务器端启动
70 /// </summary>
71 /// <returns>返回启动结果,0表示启动失败,1表示启动成功</returns>
72 [DllImport("nc.dll")]
73 public static extern int StartUp();
74
75 /**//// <summary>
76 /// 服务器端停止
77 /// </summary>
78 [DllImport("nc.dll")]
79 public static extern void Stop();
80
81 /**//// <summary>
82 /// 向指定的套接字投递一个接收指令,服务器端将异步接收
83 /// </summary>
84 /// <param name="sock">指定的套接字</param>
85 [DllImport("nc.dll")]
86 public static extern void Receive(int sock);
87
88 /**//// <summary>
89 /// 向指定的套接字投递一个发送指令,服务器端将异步发送
90 /// </summary>
91 /// <param name="sock">指定的套接字</param>
92 /// <param name="buf">待发送的数据</param>
93 /// <param name="buflen">发送的数据长度,= buf.Length</param>
94 [DllImport("nc.dll")]
95 public static extern void Send(int sock, byte[] buf, int buflen);
96
97 /**//// <summary>
98 /// 与和指定套接字连接的客户端断开连接
99 /// </summary>
100 /// <param name="sock">指定的套接字</param>
101 [DllImport("nc.dll")]
102 public static extern void ShutDown(int sock);
103
104 /**//// <summary>
105 /// 设置最大连接数,默认1000
106 /// </summary>
107 /// <param name="maxConnection">连接数</param>
108 [DllImport("nc.dll")]
109 public static extern void SetMaxConnection(int maxConnection);
110
111 /**//// <summary>
112 /// 设置当服务器端接收到连接时的自定义响应
113 /// </summary>
114 /// <param name="cbf">委托实例,请用成员变量保存,否则被GC后会报异常</param>
115 [DllImport("nc.dll")]
116 public static extern void SetAcceptConnectFP(OnAccepted cbf);
117
118 /**//// <summary>
119 /// 设置当服务器端接收到数据时的自定义响应
120 /// </summary>
121 /// <param name="cbf">委托实例,请用成员变量保存,否则被GC后会报异常</param>
122 [DllImport("nc.dll")]
123 public static extern void SetDataReceivedFP(OnDataReceived cbf);
124
125 /**//// <summary>
126 /// 设置当服务器端数据发送完毕时的自定义响应
127 /// </summary>
128 /// <param name="cbf">委托实例,请用成员变量保存,否则被GC后会报异常</param>
129 [DllImport("nc.dll")]
130 public static extern void SetDataSentFP(OnDataSent cbf);
131
132 /**//// <summary>
133 /// 设置当客户端断开连接时的自定义响应
134 /// </summary>
135 /// <param name="cbf">委托实例,请用成员变量保存,否则被GC后会报异常</param>
136 [DllImport("nc.dll")]
137 public static extern void SetHandleDisconnectFP(OnDisconnected cbf);
138 }
其中在.Net环境下使用时要注意两点:
1、 在指定自定义的委托实例时,需要用成员变量来保存委托实例。使用局部或临时变量来保存委托实例的话,变量在其作用域外就会被垃圾回收,这样当它异步回调委托时就会报错。
2、 读取接收到的数据时,需要把数据从非托管的内存拷贝到托管的内存,具体请见:C++ Dll回调C#方法。
它开放了一些设置的接口,但是一般情况下使用其默认配置即可。所以一般情况下,其调用顺序为:
SetAcceptConnectFP、SetDataReceivedFP、SetDataSentFP、SetHandleDisconnectFP、SetListenPort à StartUp à Receive、Send、ShutDown、IsStartUp à Stop。