read returns EINVAL after 2^31 chars
David Steffens
das at eplunix.UUCP
Thu Jan 11 06:27:11 AEST 1990
Subject:
Read/write return EINVAL after 2^31 chars have been read/written.
File:
sys/sys_inode.c
Repeat-by:
Try to read more than 2^31 characters from a character device.
See read return EINVAL. Fails with write, too.
You may prefer inspection -- takes a few hours, even on a Sun4!
Discussion:
This bug was first discovered in a SunOS4.0.3 binary
and traced back to the 4.3bsd (and 4.2bsd) sources.
It appears to have been introduced by a too-hasty
translation of imprecise English logic into C.
What seems to have been expressed in English was:
IF the offset is negative AND
it isn't a character device OR
it isn't the memory device
THEN return EINVAL.
Unfortunately, when this was coded it became:
IF the offset is negative AND EITHER
NOT a character device OR
NOT the memory device
THEN return EINVAL.
This causes EINVAL to be returned for EVERY character device
EXCEPT the memory device.
Seems to me what really should have been expressed (and coded) was:
IF the offset is negative AND NEITHER
a character device NOR
the memory device
THEN return EINVAL.
Fix:
*** sys/sys_inode.c0 Thu Jun 5 03:08:12 1986
--- sys/sys_inode.c Wed Jan 10 14:18:55 1990
***************
*** 94,101 ****
panic("rwip");
if (rw == UIO_READ && uio->uio_resid == 0)
return (0);
if (uio->uio_offset < 0 &&
! ((ip->i_mode&IFMT) != IFCHR || mem_no != major(dev)))
return (EINVAL);
if (rw == UIO_READ)
ip->i_flag |= IACC;
--- 94,107 ----
panic("rwip");
if (rw == UIO_READ && uio->uio_resid == 0)
return (0);
+ /*
+ * The following is the correct logic:
+ * if (uio->uio_offset < 0 &&
+ * !((ip->i_mode&IFMT) == IFCHR || major(dev) == mem_no))
+ * DeMorgan's therorem can be used to get a simpler expression, however.
+ */
if (uio->uio_offset < 0 &&
! (ip->i_mode&IFMT) != IFCHR && major(dev) != mem_no)
return (EINVAL);
if (rw == UIO_READ)
ip->i_flag |= IACC;
--
{harvard,mit-eddie,think}!eplunix!das David Allan Steffens
243 Charles St., Boston, MA 02114 Eaton-Peabody Laboratory
(617) 573-3748 Mass. Eye & Ear Infirmary
More information about the Comp.bugs.4bsd.ucb-fixes
mailing list