Polling, Fifos, and Linux

Andreas Kostyrka andreas at kostyrka.org
Fri Jul 8 09:29:31 EDT 2005


On Thu, Jul 07, 2005 at 10:21:19PM -0700, Jacob Page wrote:
> Jeremy Moles wrote:
> > This is my first time working with some of the more lower-level python
> > "stuff." I was wondering if someone could tell me what I'm doing wrong
> > with my simple test here?
> > 
> > Basically, what I need is an easy way for application in userspace to
> > simply echo values "down" to this fifo similar to the way proc files are
> > used. Is my understanding of fifo's and their capabilities just totally
> > off base?
> 
> You shouldn't need to use select.poll(), unless I'm missing something. 
> I was able to get the following to work:
Ok, you miss something ;) The program you proposed does busy waiting
and without a time.sleep call will consume 100% CPU time :(

Actually, with a named fifo the situation gets even nastier:

import os, select, time

fifo = os.open("fifo", os.O_RDONLY)

while True:
    print "SELECT", select.select([fifo],[],[])
    string = os.read(fifo, 1)
    if len(string):
        print string
    else:
        nf = os.open("fifo", os.O_RDONLY)
        os.close(fifo)
        fifo = nf
    # Perhaps add a delay under an else

The problem is, that select (and poll) show a End-Of-File condition by returning
ready to read. But on a FIFO, when the first client terminates, the reading
end goes into a EOF state till somebody else reopens the fifo for writing.

[This bit of wisdom comes Advanced Programming in the UNIX Environment by 
W.R. Stevens p. 400: 'If we encounter the end of file on a descriptor, that
descriptor is considered readbale by select.']

closing the old descriptor must be done after opening a new one, or else you
get a tiny moment where a O_WRONLY client is not able to open the file.
This way there is always a reading client of the fifo.

Andreas


> 
> -=-=-
> 
> import os
> 
> fifo = os.open("fifo", os.O_RDONLY | os.O_NONBLOCK)
> 
> while True:
>      string = os.read(fifo, 1)
>      if len(string):
>          print string
>      # Perhaps add a delay under an else
> 
> -=-=-
> 
> The Python script, when run, does nothing until you put data into the 
> fifo from another process.  Then it immediately spits the data out, 
> character by character.
> 
> I'm assuming that you've already created the fifo and that it's in the 
> current working directory.
> -- 
> http://mail.python.org/mailman/listinfo/python-list



More information about the Python-list mailing list