找回密码
 立即注册

扫一扫,访问微社区

QQ登录

只需一步,快速开始

查看: 2969|回复: 2

[求助] 大佬们速来,python多进程如何传递epoll?

1

主题

1

帖子

1

积分

贫民

积分
1
回复看了电 发表于 2019-6-11 19:52:19 | 显示全部楼层 |阅读模式

复制代码
  1. process_num = 2*cpu_count()
  2.         # 设置进程池、消息队列
  3.         po = Pool(process_num)
  4.         q = Manager().Queue() #ipc方法1
  5.         m=Manager()  # ipc方法2

  6.         # 初始化并监听epoll
  7.         epoll_fd = select.epoll()
  8.         epoll_fd.register(serverSocket.fileno(), select.EPOLLIN)

  9.         connections = {}
  10.         addresses = {}
  11.        

  12.         # 循环接收请求
  13.         while True:
  14.                 # epoll 进行 fd 扫描的地方 -- 未指定超时时间则为阻塞等待
  15.                 epoll_list = epoll_fd.poll()
  16.                 for fd, events in epoll_list:
  17.                         print("fd is:%s events is%s"%(fd,events))
  18.                         if fd == serverSocket.fileno():

  19.                                 conn, addr = serverSocket.accept()
  20.                                 conn.setblocking(False)
  21.                                 epoll_fd.register(conn.fileno(), select.EPOLLIN  | select.EPOLLET )

  22.                                 connections[conn.fileno()] = conn
  23.                                 addresses[conn.fileno()] = addr


  24.                         elif events & select.EPOLLIN:
  25.                                
  26.                                
  27.                                
  28.                                 q.put(connections[fd])
  29.                                 po.apply_async(workProcess4In,(q,epoll_fd)) # 非阻塞-进程池

  30.                         elif events & select.EPOLLOUT:
  31.                                 q.put(fd)
  32.                                 # d=m.dict({"epollfd":epoll_fd,"fd":fd})
  33.                                 po.apply_async(workProcess4Out,(fd,epoll_fd))
  34.         po.close()
  35.         po.join()
  36. <div class="blockcode"><blockquote>def workProcess4In(q):
  37.         # print("消息队列有:%s"%q.qsize())
  38.         print("共享内存 is:%s"%q)
  39.         # d["epollfd"].modify(d["fd"],select.EPOLLET | select.EPOLLOUT)
  40.         # a = q.get()
  41.         # 实验性,不行就放共享内存
  42.         # epoll_fd = select.epoll()
  43.         # epoll_list1 = epoll_fd.poll()
  44.         print(epoll_list)
  45.         # print("epoll2 is:%s"%epoll_fd)
  46.         # print("a的文件描述符是%s"%a[1])
  47.         epoll_fd.modify(a, select.EPOLLET | select.EPOLLOUT)
复制代码


半同步半异步。主进程负责接收请求,收到请求后,分发给其他进程处理。现在都问题是:epoll_fd传不过去其他进程。无论是用代码里面都q,还是m。2个IPC方法都不行。或者直接在apply_async的参数传。都无法传过去。困扰很久,请大佬们帮帮忙
回复

使用道具 举报

0

主题

2

帖子

2

积分

贫民

积分
2
懒画眉 发表于 2021-3-21 15:48:32 | 显示全部楼层
最后有没有解啊,多进程间的pipe也不行吗?
回复 支持 反对

使用道具 举报

0

主题

2

帖子

2

积分

贫民

积分
2
懒画眉 发表于 2021-3-21 16:27:13 | 显示全部楼层
epoll事件机制在内核层有个惊群效应,epoll事件的到来会唤醒监听在这个端口上的所有进程,这些进程在执行accept操作的时候内核只会唤醒一个进程,这个client的fd就会只存在在一个进程里,epoll事件会唤醒所有的进程,但event只在一个client的fd上。建议看看epoll惊群现象的描述,nginx为了减缓这种惊群现象使用了锁机制。
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

快速回复 返回顶部 返回列表