[lkml]   [1998]   [Jun]   [24]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
Messages in this thread
    SubjectRe: Thread implementations, poll, etc.
    Mike Ditto writes:
    > I just got caught up on 3 days worth of interesting discussion; here are
    > some points that I didn't see made. Everything I say here about poll()
    > applies equally to select(), of course.

    Have you read: ?

    > Someone said that if regular files supported poll(), "tail -f" could use
    > poll() instead of sleep(). This is not true; it is a common
    > misconception about what poll actually does. A poll for reading doesn't
    > mean "wake me when there are data which I can read". It means "wake me
    > when a read() would not block interruptibly. A read() on a regular file
    > will never block interruptibly (at least by tradition, interruptible NFS
    > mounts notwithstanding). Regular files already support poll() fully and
    > correctly.


    > Someone said that poll on regular files is the same as async I/O. It
    > isn't. poll isn't I/O at all. Operations under any async I/O paradigm
    > actually perform I/O and notify asynchronously of completion. poll
    > never performs I/O, it only gives the caller stale information about
    > whether certain hypothetical I/O operations would block. This is one of
    > the flaws in select, poll, ioctl(FIONREAD) and similar kludges. Between
    > the time that the call returns and the time you try to do something
    > about it, things can change. If you are correctly using non-blocking
    > operations, this is probably only a performance problem (you would just
    > loop back into another poll), but if you assume that the information
    > from poll is more than a hint, you can reach deadlock or some other
    > failure.
    > True async I/O requires that the actual I/O be asynchronous, not just a
    > mechanism for waiting until it is safe to do synchronous I/O.


    > Someone claimed that poll() could benefit from a wake-one implementation
    > or option. This doesn't make sense for two reasons. First, it just
    > doesn't make sense to have more than one context polling for the same
    > readiness condition, for the reasons above. Second, after the chosen
    > thread is awoken, what should happen to the other polling threads? They
    > are still in a poll() system call, one of the file descriptors they are
    > polling is ready, and there is no real guarantee that the awoken thread
    > will do anything with the ready fd any time soon. It may have other
    > ready fds or other internal processing to do first, or just be hosed in
    > general. The situation is one where the semantics of poll() say that
    > the other threads should wake up, but you "don't want" them to, but
    > there is no reasonable condition defined for when this special exception
    > period should end.
    > poll() is a substitute for multithreading and just wasn't meant to work
    > well in conjunction with multithreading. Because of the nature of
    > poll() it is most robust to multiplex your polling of any one condition
    > through one thread and pass off the events to other threads, even though
    > this has unfortunate performance costs.


    > Someone wondered what it would mean to be polling a file descriptor and
    > have that file descriptor become closed (either by closing it in another
    > thread, or by using some new asynchronous form of polling). The proper
    > semantics of poll() say that the poll should immediately report the
    > closed file descriptor as "ready" because a read() would not block, it
    > would immediately return (with EBADF).

    I don't recall seeing that. I did speculate what should happen if a FD
    is ready, causing a event message to be sent, and then the FD is
    closed by a different thread. Different story from poll(2) and closing
    FDs, though.

    > Some people proposed various forms of asynchronous I/O or asynchronous
    > polling. Asynchronous I/O is not a bad idea, but it is a very different
    > paradigm from that of Unix. I find the idea of asynchronous polling,
    > however, absolutely hideous. It just adds a messy, complex interface on
    > top of a flawed incomplete alternative to true threads. An asynchronous
    > programming model would be much better based on true async I/O, with
    > completion messages indicating that the I/O is complete.

    Don't recall seeing that one.

    > But all currently implemented or proposed asynchronous I/O schemes (of
    > course there probably some of which I am not aware) are still incomplete
    > alternatives to threads. There are many operations for which one needs
    > to wait that are not strictly I/O operations, or at least do not use the
    > read/write/file descriptor model. Examples: wait(), connect(),
    > pause(). Threads are really the only way to get everything right.

    We want to be careful not to create zillions of threads, though, as
    they have a cost too.

    > The idea of implementing async I/O on top of threads seems completely
    > backward to me. If I were designing and implementing a OS from scratch,
    > I would have the kernel provide only asynchronous I/O, and no threads.
    > Every single system call would be asynchronous in structure, although
    > most operations would no doubt be marked as already completed when the
    > trap returned. One version of libc would wrap these asynchronous calls
    > inside synchronous wrappers, doing an explicit wait for completion after
    > every call, providing a traditional Unix-like model. Another version of
    > libc would implement threads, doing a wait for completion only when all
    > threads were sleeping. Another version of libc could make the
    > asynchronous interfaces themselves available.

    If userland AIO (using threads) works just as well as a kernel-space
    AIO implementation, then there is no need for a kernel-space
    implementation. We'll only know if both scheme are implemented and

    > Note that the above hypothetical system fails to give any parallelism
    > benefit to a single running process on a MP system. This is fine by me.
    > Threads are a programming paradigm, not a perfomance tool. If you want
    > parallelism, use fork().

    Not for my parallel rendering task, thanks. I'll use threads: it's a
    more natural environment than fork(2).

    > I'm sure at least that last statement will get some disagreement. :)




    To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
    the body of a message to

     \ /
      Last update: 2005-03-22 13:43    [W:0.027 / U:41.232 seconds]
    ©2003-2016 Jasper Spaans. hosted at Digital OceanAdvertise on this site