Skip site navigation (1)Skip section navigation (2)
Date:      Fri, 24 Oct 1997 13:08:26 -0400 (EDT)
From:      spork <spork@super-g.com>
To:        tqbf@enteract.com
Cc:        freebsd-security@FreeBSD.ORG
Subject:   Re: BoS: Possible SERIOUS bug in open()? (fwd)
Message-ID:  <Pine.BSF.3.96.971024125748.21468B-100000@super-g.inch.com>
In-Reply-To: <19971023063636.19963.qmail@joshua.enteract.com>

next in thread | previous in thread | raw e-mail | index | archive | help
I see a fix for RELENG_2_2 at:

http://www.freebsd.org/cgi/cvsweb.cgi/src/sys/kern/vfs_syscalls.c

but has anyone by chance back-ported this to 2.1.x?

Thanks,

Charles


On 23 Oct 1997 tqbf@joshua.enteract.com wrote:

> In muc.lists.freebsd.security, you wrote:
> >  fd = open("/dev/rsd0a", -1, 0);
> 
> Yep. This definitely works on {Free,Net,Open}BSD.
> 
> This is a variant of a bug Theo de Raadt found in SunOS back in the 1980s.
> The basic issue is that the code that guards access to the device-specific
> open() routine checks explicitly for FREAD, FWRITE, and O_TRUNC, and
> passes the call through if none of these are set. Theo's bug involved
> using "3" for the open() flag. 
> 
> The problem here is that before calls to open() are even passed to the
> vnode open() routine (after the vnode is looked up by the generic
> vfs_syscalls open() syscall handler), the flags field is incremented by
> one:
> 
> vfs_syscalls.c:open()
> 
> 	...
> 
>         flags = FFLAGS(uap->flags);
> 
> 	...
> 
> where FFLAGS() is:
> 
> ./sys/fcntl.h:#define  FFLAGS(oflags)  ((oflags) + 1)
> 
> As you can see, passing a "-1" to open() will result in "flags" becoming 
> "0" - open() ordinarily never passes "0" to the vnode code, since "0"
> becomes "1" after being converted to fflags format.
> 
> A fun game you can play with practically no programming ability is to
> exploit the fact that some devices will initialize themselves immediately
> upon being opened - particularly amusing is the SCSI tape driver,
> sys/scsi/st.c, which will rewind itself when opened. Simply run the
> previously posted example code on /dev/rst0 and destroy tonight's backup.
> 
> If you want to hack this fixed in FreeBSD, you can apply the enclosed diff
> to your kernel; this is a total hack, and someone else will provide a
> "correct" fix soon enough. 
> 
> Incidentally, this is yet another piece of evidence supporting the
> presence of another systemic secure-coding problem - sanity checking
> integer arguments and guarding against overflow. This is far from the only
> place that I've seen problems with unexpected interactions owing to
> surprise negative arguments. Anyone want to take a guess as to what
> strncpy() does when it gets a negative "count" argument? Think that can't
> happen? Think pointer arithmetic.
> 
> -- 
> -----------------------------------------------------------------------------
> Thomas H. Ptacek					Secure Networks, Inc.
> -----------------------------------------------------------------------------
> 					   	     "mmm... sacrilicious..."
> 
> --- vfs_syscalls.c-orig Thu Oct 23 01:21:58 1997
> +++ vfs_syscalls.c      Thu Oct 23 01:21:19 1997
> @@ -690,6 +690,9 @@
>                 return (error);
>         fp = nfp;
>         flags = FFLAGS(uap->flags);
> +       if(!flags)
> +               flags++;
> +
>         cmode = ((uap->mode &~ fdp->fd_cmask) & ALLPERMS) &~ S_ISTXT;
>         NDINIT(&nd, LOOKUP, FOLLOW, UIO_USERSPACE, uap->path, p);
>         p->p_dupfd = -indx - 1;                 /* XXX check for fdopen */
> 




Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?Pine.BSF.3.96.971024125748.21468B-100000>