Front page | perl.perl5.porters |
Postings from May 2004
Re: [perl #29277] eof() on non-blocking filehandle
Thread Previous
|
Thread Next
From:
Dave Mitchell
Date:
May 4, 2004 14:45
Subject:
Re: [perl #29277] eof() on non-blocking filehandle
Message ID:
20040504215002.GE1884@iabyn.com
On Fri, Apr 30, 2004 at 12:09:05PM -0000, perl-5. 8. 0 @ ton. iguana. be wrote:
> Using this testprogram:
>
> #! /usr/bin/perl -wl
> use strict;
> use IO::Socket::INET;
> use POSIX qw(F_GETFL F_SETFL O_NONBLOCK);
>
> pipe(my $rd, my $wr) || die "Could not create pipe: $!";
> my $flags = fcntl($rd, F_GETFL, 0) || die "Can't get fcntl flags: $!\n";
> fcntl($rd, F_SETFL, $flags | O_NONBLOCK) || die "Can't set fcntl flags: $!\n";
> select($wr);
> $|=1;
> close($wr) if @ARGV;
> my $rc = eof($rd);
> print STDERR defined($rc) ? $rc : "undef", "/$!";
>
> Running it with an argument:
> 1/Illegal seek
The value of $! is irrelevant; it's only relevant on failed perl system
functions.
> Now without argument (not closing the write side of the pipe):
> 1/Illegal seek
>
> mm, but there is no EOF this time....
>
> Again looking at the strace:
>
> pipe([3, 4]) = 0
> ioctl(3, SNDCTL_TMR_TIMEBASE, 0xbfffeb40) = -1 EINVAL (Invalid argument)
> _llseek(3, 0, 0xbfffeb90, SEEK_CUR) = -1 ESPIPE (Illegal seek)
> ioctl(4, SNDCTL_TMR_TIMEBASE, 0xbfffeb40) = -1 EINVAL (Invalid argument)
> _llseek(4, 0, 0xbfffeb90, SEEK_CUR) = -1 ESPIPE (Illegal seek)
> fcntl64(3, F_SETFD, FD_CLOEXEC) = 0
> fcntl64(4, F_SETFD, FD_CLOEXEC) = 0
> fcntl64(3, F_GETFL) = 0 (flags O_RDONLY)
> fcntl64(3, F_SETFL, O_RDONLY|O_NONBLOCK) = 0
> read(3, 0x8175804, 4096) = -1 EAGAIN (Resource temporarily unavailable)
> brk(0) = 0x82bc800
> brk(0x82be000) = 0x82be000
> write(2, "1", 11) = 1
> write(2, "/Illegal seek", 13/Illegal seek) = 13
> write(2, "\n", 1
> ) = 1
> close(3) = 0
> close(4) = 0
>
> So the read got EAGAIN (so perl should know it's not really EOF),
> but eof() still returns true, but i think it should have returned
> something false here. The errno is also strange (seemingly that old
> ESPIPE got saved and later restored, overwriting the EAGAIN).
Perl's eof is implemneted by going a getc and ungetc equivalent;
since these can change $!, but the Perl function eof() is documented
as not seeing $!, the old value has to be saved then restored.
Agin, the value of $! here is a bit of red herring.
The real issues, are whether eof() should be clever enough to understand
and handle non-blocking I/O (I presume that EAGAIN is system specific, at
least outside the UNIX world!), or whether this falls into the category
of mixing raw and buffered I/O, and thus get everything you deserve?
I guess NI-S might be able to comment better on this.
Dave.
--
"The GPL violates the U.S. Constitution, together with copyright,
antitrust and export control laws"
-- SCO smoking crack again.
Thread Previous
|
Thread Next