• tcp通信:多进程共享listen socket方式


    原文链接:http://blog.csdn.net/largetalk/article/details/7939080

    看tornado源码多进程(process.py)那段,发现他的多进程模型和一般常见的模型有点不一样,多见的是主进程bind-> listen -> accept, 将accept返回的socket用子进程处理,而tornado是在bind -> listen -> fork, 在listen之后fork,多个子进程共享listen socket, 每个子进程都accept。 以前没见过这种模型,开始觉的会有 错误或"惊群“现象的发生,网上找了一下也没有找到相关资料,自己就写了个程序测试一下。

    [python] view plaincopyprint?
     
    1. import socket  
    2. import select  
    3. import os  
    4. import time  
    5. import errno  
    6.   
    7. def child_epoll():  
    8.     epoll = select.epoll()  
    9.     epoll.register(sock.fileno(), select.EPOLLIN)  
    10.     try:  
    11.         while True:  
    12.             events = epoll.poll(1)  
    13.             for fileno, event in events:  
    14.                 if fileno == sock.fileno():  
    15.                     connection, address = sock.accept()  
    16.                     print os.getpid(), address  
    17.                     time.sleep(1)  
    18.                     connection.close()  
    19.     finally:  
    20.         epoll.unregister(sock.fileno())  
    21.         epoll.close()  
    22.   
    23.   
    24. def start_child(i):  
    25.     pid = os.fork()  
    26.     if pid == 0:  
    27.         child_epoll()  
    28.     else:  
    29.         children[pid] = i  
    30.   
    31. sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM, 0)  
    32. sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)  
    33. sock.setblocking(0)  
    34. sock.bind(("0.0.0.0", 9700))  
    35. sock.listen(128)  
    36.   
    37.   
    38. children = {}  
    39.   
    40. for i in range(4):  
    41.     start_child(i)  
    42.   
    43. time.sleep(2)  
    44. print children  
    45. while children:  
    46.     try:  
    47.         pid = status = os.wait()  
    48.     except OSError, e:  
    49.         if e.errno ==  errno.EINTR:  
    50.             continue  
    51.         raise  
    52.     if pid not in children:  
    53.         continue  
    54.     children.pop(pid)  
    55.   
    56. sys.exit(0)  


    然后用ab简单测测: ab -n 10 -c 5 http://127.0.0.1:9700/

    可以发现每个连接都会只有一个进程去处理。虽然逻辑上没有错误,但还是要找相关资料看看,有知道的请告诉我一下。

    后补:(20121101)

    http://blog.dccmx.com/2011/02/nginx-conn-handling/ 介绍nginx多进程模型就是如此工作,nginx使用一个全局锁来避免惊群

    http://static.usenix.org/event/usenix2000/freenix/full_papers/molloy/molloy.pdf 该论文说linux 2.6内核之后accept不会有惊群现象

  • 相关阅读:
    笔试材料收集(二)——用OPENGL搞个冒泡排序,原创_!
    cocos2dx andoroid切换后台后资源重载
    ipa命令行打包命令
    SceneManager
    ios上遇到过的问题集及解决方法(1)
    google inapp billing
    Unity Editor学习IHasCustomMenu
    cocos2dx如果更好地使用第三库
    cocos2dhtml环境布暑
    ios中,常用的一些调试命令
  • 原文地址:https://www.cnblogs.com/johnnyflute/p/3969705.html
Copyright © 2020-2023  润新知