开发者

Interrupting Select to add another socket to watch in Python

开发者 https://www.devze.com 2023-02-04 09:38 出处:网络
I\'m implementing peer-to-peer IPC using TCP in a Windows XPapplication. I\'m using the select and socket modules in Python 2.6.6.

I'm implementing peer-to-peer IPC using TCP in a Windows XP application.

I'm using the select and socket modules in Python 2.6.6.

I have three TCP threads, a reading thread that typically is blocking on select(), a writing thread that is typically waiting on an event (the event indicates there is stuff to write to TCP) and a listening thread that accepts connections.

If I start a new connection or close a current one then I need to interrupt the read select and restart it so it listens to the newly accepted socket as well.

Under wi开发者_如何学运维nsock I can call WSACancelBlockingCall which will interrupt the select gracefully.

So my question is this: is it possible to do all this in a pythonic way without resorting to using poll()?

Many thx

--DM


You could try adding an extra file descriptor to your set that you use as a signaling mechanism. You can then write to that descriptor a dummy value to cause select to exit. For example:

my_pipe = os.pipe()
...
while True:
    ready_fds = select.select(my_read_fds + [my_pipe[0]],
                              my_write_fds, my_except_fds, timeout)
    if my_pipe[0] in ready_fds[0]:
        # Add another fd to my_read_fds, etc.
        os.read(my_pipe[0], 1)
    ...

# To interrupt the current select call and add a new fd, write to the pipe:
os.write(my_pipe[1], 'x')


I am not able to add comments, so I'm adding this as an answer.

Don't use WSACancelBlockingCall. You should use the approach from Adam Rosenfield's answer. Just make a pair of dummy sockets one connected to another, instead of a dummy file descriptor. Include one of that sockets in your select() call. When you need to interrupt the call - just write a byte into the second dummy socket.

Oh, and don't forget to read that byte back from the first socket when select() will return.

0

精彩评论

暂无评论...
验证码 换一张
取 消