半年前偶然看到一叫spserver的服务器框架,它将windows下IOCP移植到到libevent,并且以HSHA,LF两种模式实现了服务器框架.我做了点功课,写点心得.
一般来说在设计一个服务器网络框架的时候,需要用到线程池,里面的线程负责执行服务端所有代码.这些代码总的来说可以分为两类:
- 一类负责网络IO部分,也就是从网络读取和发送数据
- 另一类负责处理各种业务逻辑.
通常情况下他们是分离的,网络IO部分不需要管理业务逻辑具体做什么工作,而后者也不关心数据怎么得来,怎么送到网络上.两者就是一个生产者消费者关系.
这里讨论的HSHA就是网络IO部分为异步模式,而业务逻辑部分为同步模式.即:
- 网络IO请求为非阻塞的异步操作,只要调用了,就立即返回,操作结果不用调用方不断的去问:”发送/接收成功了吗?”.网上有一个比较形象的比喻,叫经典的好莱坞法则:你不用给我们打电话,我们会通知你的(you dont call me,i will call you).
- 业务逻辑部分是同步的,虽然不确定服务端线程池中,到底是哪一个线程在执行,但同一时刻只会有一个线程在执行这个网络会话上的业务逻辑.
同步和异步两部分采用一个作业队列(jobQueue)来实现结合,一些细节:
- 服务端定义一组回调函数,用于将网络连接上的OnAccept,OnRecv,OnSend,OnClose等事件通知业务逻辑层,而业务逻辑层的实现代码正是在这些回调函数中实现.
- 网络连接建立时,服务端会创建一个网络会话对象,并保存有相关回调函数的指针.将回调函数OnAccept和相关上下文打包成一个任务push到作业队列.
- 网络连接收到数据后,服务端将回调函数OnRecv和相关上下文打包成一个任务push到作业队列.
- 网络连接发送数据后,服务端将回调函数OnSend和相关上下文打包成一个任务push到作业队列.
- 网络连接关闭后,服务端将回调函数OnClose和相关上下文打包成一个任务push到作业队列.
- 负责执行作业的某个线程被唤醒,取出这些作业,并执行.
以下代码说明大概的处理流程:
1: class job_queue;
2: class msg_free_queue;
3: class thread_pool;
4: int main()
5: {
6: job_queue jobs;
7: msg_free_queue msg_to_free;
8: thread_pool job_thread;
9: thread_pool clean_thread;
10: server_init_and_listen();
11: run_accept_thread();
12: while(!exit_falg){
13: run_iocp_event_loop(&jobs,&msg_to_free);
14: while(job_queue.size() > 0){
15: job_thread.push(job_queue.pop_front());
16: }
17: while(msg_to_free.size() > 0){
18: clean_thread.push(msg_to_free.pop_front());
19: }
20: };
21: }
主线程负责完成端口事件的处理,并完成作业任务的打包,保存在一个容器中.
以上代码只说明了服务端如何把IO层收到的数据交给逻辑层,并没有解释逻辑层怎么样把数据交给IO层发送,实际上这个工作是在负责调用回调函数的那个线程完成,当回调函数返回后,作业线程直接将需要发送的数据打包成一个完成事件,post到完成端口句柄上,这样就建立起关系了.
由于是异步的,逻辑层发送的数据不能确定什么时候发送出去,因此需要保存起来,当完成事件到达后,会把已经发送的数据指针放到一个容器中,然后由主线程负责处理善后问题.
下面是一些题外话:
你也看到了,只有一个线程负责处理IO部分,那么性能如何呢?
这个吧,其实大多数时候,你的服务器性能瓶颈不再网络IO部分,而在业务逻辑处理部分,在那里可能产生磁盘IO,数据库操作等.我个人觉得但线程IO已经足够了.采用IOCP这样高效的IO模型是为业务逻辑处理腾出资源,因为一个高效的服务端不是看你每秒能收发多少数据,而是看业务处理能力.另外单线程的IOCP也有很多好处,首先就是锁的问题解决了,其次就是资源的管理简单了,这两个问题都是比较棘手的东西.
我编译了spserver的代码,用asio的乒乓测试客户端程序做了一下压力测试,结果你可能也猜到了,IO吞吐量并不算很高,而且多核CPU上,只有一个CPU达到了100%利用率,而另外几个CPU则利用率不足50%.如果你跟我一样,是一个完美主义者,我们可以这样改进它:
将上面的代码中,监听工作和Accept线程分离出来,主循环那的部分(while那一块和相关的上下文环境)封装成一个模块,每一个模块都有自己完成端口句柄,当连接建立时,做一个简单的负载均衡,为新建立的连接的套接字句柄选择一个完成端口句柄并绑定.于是就变成了下面的样子:
1: class job_queue;
2: class msg_free_queue;
3: class thread_pool;
4: int nod();
5: int main()
6: {
7: thread_pool io_thread_nods;
8: io_thread_nods.set_thread_count(4);
9: server_init_and_listen();
10: run_accept_thread();
11: while(true){
12: io_thread_nods.run(nod);
13: }
14: }
15: int nod()
16: {
17: job_queue jobs;
18: msg_free_queue msg_to_free;
19: thread_pool job_thread;
20: thread_pool clean_thread;
21: while(!exit_falg){
22: run_iocp_event_loop(&jobs,&msg_to_free);
23: while(job_queue.size() > 0){
24: job_thread.push(job_queue.pop_front());
25: }
26: while(msg_to_free.size() > 0){
27: clean_thread.push(msg_to_free.pop_front());
28: }
29: };
30: }
OK,完工.
文章信息
作者:J.Cheen
出处:www.cnblogs.com/cheen
分享到:
相关推荐
标题中提到的"threadpool"直译为“线程池”,而描述中提到了两种特定的线程池模型:半同步半异步(Half-Synchronous Half-Asynchronous,简称HSHA)模型和Leader-Follower模型。这两种模型都是为了优化线程池的性能...
服务端:支持Apache Thrift的各种原生服务线程模型,包括单线程阻塞模型(simple)、单线程非阻塞模型(nonBlocking)、线程池阻塞模型(threadPool)、半同步半异步模型(hsHa)和半同步半异步线程选择器模型...
"HSHA驱动报警信息解决方案" 本解决方案旨在为HSHA驱动报警信息提供解决方案,涵盖了HSHA伺服驱动器的故障类型、故障原因、故障响应动作和故障处理对策。 一级故障列表 * Err 01: E2PROM 读取错误 + 故障原因: ...
HSHA驱动器报警说明书 HSHA驱动器报警说明书是一份详细的故障手册,旨在帮助用户快速identify和解决HSHA伺服驱动器中的故障。该手册提供了详细的故障列表,包括故障号、故障名称、故障响应动作等信息。 一级故障...
传统的并发模型,如半同步半异步(HsHa),虽然简单,但在处理IO密集型任务时效率较低,因为它们依赖于锁机制。为了改进这种模型,我们可以考虑以下两个方向: 1. **I/O操作的异步化和非阻塞**:通过非阻塞I/O,...
### 不同启动子对禽流感病毒H5HA基因在马铃薯体中表达的影响 #### 研究背景与意义 禽流感(Avian influenza, AI)是一种由A型流感病毒引起的急性传染病,该病毒对家禽养殖业造成了巨大损失,并且对人类健康构成了...
沈阳机床(上海)智能系统研发设计有限公司作为一家专注于运动控制技术和云制造技术研发的企业,已经成功研发出了一系列面向机床行业的产品,如i5系列智能数控系统、HSHA系列伺服驱动器以及WIS车间信息系统等。...
c# 如何实现MD5,SHA1,SHA256,SHA512等常用加密算法,需要的朋友可以参考下
import java.io.UnsupportedEncodingException; import java.security.MessageDigest; import java.security.NoSuchAlgorithmException; public class Sha256 { public static String getSHA256(String str){ ...
该公司的i5系列智能数控系统、HSHA系列伺服驱动器以及WIS车间信息系统等一系列产品,为智能化制造提供了坚实基础。 工业App,尤其是视觉识别App,是该解决方案的核心部分。它在i5OS平台上运行,通过相机捕捉图像并...
在本项目中,我们主要探讨的是利用斑点鬣狗算法(Hybridized Spotted Hyena Algorithm,HSHA)优化BP神经网络(Backpropagation Neural Network)以实现数据预测的MATLAB实现。斑点鬣狗算法是一种新兴的生物启发式...
该公司已自主研发了一系列产品,如i5系列智能数控系统、HSHA系列伺服驱动器及WIS车间信息系统。该公司将i5运动控制核心技术进行了模块化封装,并以平台形式向社会开放,打造了一个通用的工业APP开发、应用与分享的...