Sender: rich AT phekda DOT freeserve DOT co DOT uk Message-ID: <3A63764C.2CE7F394@phekda.freeserve.co.uk> Date: Mon, 15 Jan 2001 22:14:36 +0000 From: Richard Dawe X-Mailer: Mozilla 4.51 [en] (X11; I; Linux 2.2.17 i586) X-Accept-Language: de,fr MIME-Version: 1.0 To: djgpp-workers AT delorie DOT com Subject: Re: /dev/zero & /dev/full FSEXTs References: <8632-Sat06Jan2001203659+0200-eliz AT is DOT elta DOT co DOT il> Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Reply-To: djgpp-workers AT delorie DOT com Hello. Eli Zaretskii wrote: > > + /* Ensure that we only have relevant flags. */ > > + data->flags &= (O_ACCMODE | O_BINARY | O_TEXT | O_NOINHERIT | O_NONBLOCK); > > Why do you store O_BINARY and O_TEXT? These are internal library > flags, and since there's no hook for `setmode', if the program > switches /dev/zero to a different mode, your flags will not be > correct. I was storing the flags from the open() call that seemed relevant. I have removed O_BINARY and O_TEXT now. Would an FSEXT hook for setmode() be useful? > > + case __FSEXT_ready: > > + /* This must be emulated, since the FSEXT has been called. */ > > + emul = 1; > > + > > + *rv = __FSEXT_ready_read | __FSEXT_ready_write; > > + break; > > Shouldn't /dev/full be NOT ready for writing? What does `select' > return on Unix systems for the /dev/full device in this case? As DJ said previously, you want to return ready for writing always, so that the user will get the ENOSPC error on a write. This seems similar to the principle for sockets of returning ready for reading when the peer has closed the connection - for detection of an error. > > + case __FSEXT_close: > [snip] > > + /* Cope with dup()'d zero devices. */ > > + data->dup_count--; > > + > > + if (data->dup_count <= 0) { > > + /* No longer referenced */ > > + free(data); > > + _close(fd); > > + } > > + break; > > This looks like a handle leak: you only close the handle when it is no > longer referenced. However, internal_dup _always_ calls > __FSEXT_alloc_fd, which always produces a new handle (connected to the > NUL device). So it looks like you don't close those additional > handles when the application closes them. > > Or did I miss something? No, you are quite right. I will think about that. > > + case __FSEXT_lseek: > > + fd = va_arg(args, int); > > + offset = va_arg(args, off_t); > > + whence = va_arg(args, int); > > + > > + /* This must be emulated, since the FSEXT has been called. */ > > + emul = 1; > > + > > + *rv = offset; > > Even if `offset' and `whence' point before the beginning? The handling of lseek() is a little tricky, since we have an infinitely long non-existent file. ;) SEEK_SET is easy. SEEK_CUR and SEEK_END are tricky, since they require some knowledge of how big the file is. Seeks on /dev/full are supposed to always succeed. I do not know if this is true for /dev/zero also. For our implementation, it is. What do you think the behaviour for SEEK_CUR and SEEK_END should be? Should using SEEK_END always return an offset of 0? Should using SEEK_CUR return the offset, if it's positive, else 0? Or should the code track the maximum offset and use that? > > + #include > > Is this header used on other platforms? No, it just seemed like a good name. It does not exist on Linux. Suggestions for a better name would be appreciated. > `errno' should have the @code markup, not @var, because it is not a > formal parameter but a specific variable name. Yep, fixed that. Thanks for the comments, Eli. I will assign the copyright of the /dev/zero to DJ, as soon as the papers are complete. Bye, Rich =] -- Richard Dawe http://www.bigfoot.com/~richdawe/ "The soul is the mirror of an indestructible universe." --- Gottfried W. Leibniz