NetBSD-Bugs archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

Re: kern/60792: fifo: poll reader before writers?



> Date: Sat, 26 Sep 2026 13:35:00 +0000
> From: Taylor R Campbell <riastradh%NetBSD.org@localhost>
> 
> > => Linux 6.1.0:
> >    1. read EOF                  poll 0          *bzzt*
> >    2. read EOF                  poll POLLHUP
> >    3. rd0: read EOF             poll POLLHUP
> >       rd1: read EOF             poll 0          *bzzt*
> > => FreeBSD 13.0:
> >    1. read *block*              poll 0
> >    2. read EOF                  poll POLLIN|POLLHUP
> >    3. rd0: read EOF             poll POLLIN|POLLHUP
> >       rd1: read EOF             poll 0          *bzzt*
> > [...]
> > With my naive patch for PR 60789 (to apply a change that
> > FreeBSD made back in 1997), I get:
> > 
> > => NetBSD patched for PR kern/60789:
> >    1. read EOF                  poll POLLIN|POLLHUP
> >    2. read EOF                  poll POLLIN|POLLHUP
> >    3. rd0: read EOF             poll POLLIN|POLLHUP
> >       rd1: read EOF             poll POLLIN|POLLHUP
> 
> The advantage of the Linux and FreeBSD semantics is that you can open
> a fifo for reading without blocking to get a file descriptor, and then
> use select/poll to wait for a writer to open.
> 
> But it is internally inconsistent (poll returns 0 events ready but you
> can read (EOF) without blocking!), and maybe if you want to wait for a
> connection, you should just use sockets instead of fifos anyway.
> 
> And it requires keeping per-open state rather than per-vnode state,
> which would require restructuring our fifo code, which is annoying!

Also: instead of switching to sockets, you can just keep the fifo open
for write!  That way, poll will not return ready until a byte of data
has been written.  And that semantics is guaranteed by POSIX, and
probably works everywhere already.  For totally unrelated reasons I
stumbled upon a program I wrote over a decade ago that does exactly
this, with a comment:

	/*
	 * Open the fifo for write without blocking.  We don't ever
	 * write to it, but we need it open to make poll block rather
	 * than return POLLHUP immediately in a loop.  Must happen
	 * after we open for read or else this will fail with ENXIO.
	 */

So I think I'll just go ahead with the naive patch, and if someone
really wants the semantics requiring per-open/per-vnode state (or, for
reasons I can't imagine now, longer history), they can file a new PR.



Home | Main Index | Thread Index | Old Index