mirror of
https://git.tartarus.org/simon/putty.git
synced 2025-07-04 04:52:47 -05:00
Switch to using poll(2) in place of select(2).
I've always thought poll was more hassle to set up, because if you want to reuse part of your pollfds list between calls then you have to index every fd by its position in the list as well as the fd number itself, which gives you twice as many indices to keep track of than if the fd is always its own key. But the problem is that select is fundamentally limited to the range of fds that can fit in an fd_set, which is not the range of fds that can _exist_, so I've had a change of heart and now have to go with poll. For the moment, I've surrounded it with a 'pollwrapper' structure that lets me treat it more or less like select, containing a tree234 that maps each fd to its location in the list, and also translating between the simple select r/w/x classification and the richer poll flags. That's let me do the migration with minimal disruption to the call sites. In future perhaps I can start using poll more directly, and/or using the richer flag system (though the latter might be fiddly because of sometimes being constrained to use the glib event loop). But this will do for now.
This commit is contained in:
6
putty.h
6
putty.h
@ -2052,7 +2052,7 @@ bool open_for_write_would_lose_data(const Filename *fn);
|
||||
* The reason for this is that an OS's system clock might not agree
|
||||
* exactly with the timing mechanisms it supplies to wait for a
|
||||
* given interval. I'll illustrate this by the simple example of
|
||||
* Unix Plink, which uses timeouts to select() in a way which for
|
||||
* Unix Plink, which uses timeouts to poll() in a way which for
|
||||
* these purposes can simply be considered to be a wait() function.
|
||||
* Suppose, for the sake of argument, that this wait() function
|
||||
* tends to return early by 1%. Then a possible sequence of actions
|
||||
@ -2124,12 +2124,12 @@ unsigned long timing_last_clock(void);
|
||||
* instead request notifications when a callback is available, so that
|
||||
* it knows to ask its delegate event loop to do the same thing. Also,
|
||||
* if a front end needs to know whether a callback is pending without
|
||||
* actually running it (e.g. so as to put a zero timeout on a select()
|
||||
* actually running it (e.g. so as to put a zero timeout on a poll()
|
||||
* call) then it can call toplevel_callback_pending(), which will
|
||||
* return true if at least one callback is in the queue.
|
||||
*
|
||||
* run_toplevel_callbacks() returns true if it ran any actual code.
|
||||
* This can be used as a means of speculatively terminating a select
|
||||
* This can be used as a means of speculatively terminating a poll
|
||||
* loop, as in PSFTP, for example - if a callback has run then perhaps
|
||||
* it might have done whatever the loop's caller was waiting for.
|
||||
*/
|
||||
|
Reference in New Issue
Block a user