我有一个在ZMQ Poller上轮询的线程:
poller.poll(timeout)
该线程也是通过轮询器中注册的套接字接收和发回消息的线程。
然后我有另一个线程可能最终创建一个新的套接字并注册它以轮询输入事件:
socket = context.socket(...)
socket.bind/connect(...)
poller.register(socket, zmq.POLLIN)
注册套接字后,后一个线程不会再次触摸它。
这样安全吗?
我得到的答案/评论是关于我不应该这样做的。或者是指南的建议(我已经知道)。但这并没有真正回答我的问题。
更具体地说,我会说我正在为ZeroMQ使用pyzmq
Python绑定。
现在,尽管ZeroMQ套接字不是线程安全的,但只要在传输过程中存在完整的内存屏障,它们确实可以将它们从一个线程传输到另一个线程。
所以第一个问题是:我需要在那里设置一个明确的内存屏障吗?请注意,有一个线程创建并绑定/连接套接字然后它注册它,但它不会再次使用该线程。是否存在实际冲突?我是否应该明确阻止从两个线程访问套接字?
然后第二个问题是:在poller线程安全中注册套接字?大多数情况下,执行轮询的线程忙于执行其他操作,但可能会发生轮询等待超时的情况。在这种情况下,我是否需要使用锁来阻止对轮询器的并发访问?或者在轮询器中注册新套接字而另一个线程轮询它是否安全?
我使用Pyro4来处理和配置远程进程(即:他们的ZeroMQ连接及其行为)。初始配置可以非常谨慎地使用Pyro Proxy完成。但是,当我启动进程时,我实际上正在运行主循环,其中一个专用线程(Pyro oneway call)继续运行,但如果我再次使用Pyro代理访问该对象,则此访问权限来自另一个线程
因此,我们的想法是避免修改远程对象的类,但仍然允许使用Pyro来配置远程对象,即使它们正在运行。只要创建+绑定/连接+注册新套接字对另一个线程是安全的,我就很好。