简而言之,SO_REUSEPORT套接字选项允许在ip:端口对上创建多个套接字。例如,program1和program2都可以为同一个端口和IP调用functions socket()->bind()->listen()->accept(),内核调度程序将在这两个程序之间平均分配传入的连接。
我假设有了这个选项,您就可以不用使用fork()来生成额外的工作人员,而只需运行新的程序实例。
我根据这个逻辑编写了一个简单的epoll套接字服务器,并使用加权数测试它:
weighttp -n 1000000 -c 1000 -t 4 http://127.0.0.1:8080/
对于两个运行实例,结果为~44000 RPS,对于一个运行实例--接近~51000 RPS。我非常惊讶与7000 RPS的差异。
经过这个测试,我在fork()之前添加了listen(),并运行了一个服务器实例,因此现在它具有与以前的实现相同的逻辑--使用epoll循环侦听套接字的两个进程,但是socket()->bind()只在fork()之前调用一次,第二个进程在listen()调用之前只接收FD副本。
我再次运行测试,它显示了~50000 RPS!
所以,我的问题非常简单:在这种情况下,fork()有什么魔力,为什么它的工作速度比拥有socket()的两个独立进程更快?内核为调度做同样的工作,我看不出有什么重要的区别。
发布于 2017-04-25 08:37:46
请回答这个问题:由于我的研究,内部操作系统调度程序远远不是最优的,取决于硬件。更好的做法是使用用户土地调度器。
https://stackoverflow.com/questions/28993184
复制相似问题