Sigbjorn Finne wrote: > "Dean Herington" <[EMAIL PROTECTED]> writes: > > > ... > > > > When a thread wants to read from a file descriptor, its logic looks like: > > > > threadWaitRead (fdToInt fd) > > ([char], 1) <- locked (fdRead fd 1) > > > > where `locked` obtains and holds the aforementioned lock for the duration > of > > its argument action. > > > > Reflecting on the above, I now realize that the recent change > > (/fptools/ghc/rts/Select.c?rev=1.22 in GHC 5.04) to wake up all threads > when > > select() returns an EBADF error, though well-intentioned, is > inappropriate. > > The point of `threadWaitRead` and `threadWaitWrite` is to block the > calling > > thread until it's known that a subsequent call involving the given file > > descriptor will not block. Allowing all threads to continue--even those > > whose file descriptor is not yet ready--allows for exactly the deadlock > that > > `threadWaitRead` and `threadWaitWrite` are designed to avoid. > > > > The assumption is that FDs are marked as non-blocking, so this won't > be a problem. Do you have a good reason not to have your FDs marked > as such?
One reason is complexity. If I mark my FDs with O_NONBLOCK, don't I need to wrap a loop around the `threadWaitRead`/`fdRead` combination, repeating when `fdRead` returns error `EAGAIN`? A second reason is that, even if I did the above, I'd still get deadlock on my `locked` call (which is required to support cleaning up unwanted threads in forked processes). The bottom line, in my view, is that `threadWaitRead` and `threadWaitWrite` must not return until it is sure that a subsequent read or write FD operation will return immediately, independent of the nonblocking status of the FD. > > I consider it a bug in select() that, when EBADF is reported, the sets of > > "ready" file descriptors are not also reported. > > That would be the wrong thing to do, assuming the FD_SETs are in any > way valid when select() returns failure. I don't understand your comment. I fear I wasn't clear enough. I meant that it would be better for select() to identify the FDs which are invalid in the case it returns `EBADF`. Then the clumsy code I suggested would not be necessary. Dean _______________________________________________ Glasgow-haskell-bugs mailing list [EMAIL PROTECTED] http://www.haskell.org/mailman/listinfo/glasgow-haskell-bugs
