diff options
author | peter <peter@FreeBSD.org> | 1996-05-24 16:19:23 +0000 |
---|---|---|
committer | peter <peter@FreeBSD.org> | 1996-05-24 16:19:23 +0000 |
commit | 9453593a7d6b8b4929584c55937cbc51e5de1a67 (patch) | |
tree | 6ef918bde1f5f78a10f566be17075b5cd3bc8e9e /sys/kern | |
parent | 4545233798c7d7eae3f8c4e673c91a6d2eef0622 (diff) | |
download | FreeBSD-src-9453593a7d6b8b4929584c55937cbc51e5de1a67.zip FreeBSD-src-9453593a7d6b8b4929584c55937cbc51e5de1a67.tar.gz |
Dont allow directories to be link()ed or unlink()ed, even for root
(returns EPERM always, the errno is specified by POSIX).
If you really have a desperate need to link or unlink a directory, you
can use fsdb. :-)
This should stop any chance of ftpd, rdist, "rm -rf", etc from
bugging out and damaging the filesystem structure or loosing races
with malicious users.
Reviewed by: davidg, bde
Diffstat (limited to 'sys/kern')
-rw-r--r-- | sys/kern/vfs_extattr.c | 16 | ||||
-rw-r--r-- | sys/kern/vfs_syscalls.c | 16 |
2 files changed, 18 insertions, 14 deletions
diff --git a/sys/kern/vfs_extattr.c b/sys/kern/vfs_extattr.c index ec728b3..95e9de0 100644 --- a/sys/kern/vfs_extattr.c +++ b/sys/kern/vfs_extattr.c @@ -36,7 +36,7 @@ * SUCH DAMAGE. * * @(#)vfs_syscalls.c 8.13 (Berkeley) 4/15/94 - * $Id: vfs_syscalls.c,v 1.46 1996/01/16 13:07:14 davidg Exp $ + * $Id: vfs_syscalls.c,v 1.47 1996/05/11 04:39:53 bde Exp $ */ /* @@ -886,11 +886,10 @@ link(p, uap, retval) if (error) return (error); vp = nd.ni_vp; - if (vp->v_type != VDIR || - (error = suser(p->p_ucred, &p->p_acflag)) == 0) { + if (vp->v_type == VDIR) + error = EPERM; /* POSIX */ + else { NDINIT(&nd, CREATE, LOCKPARENT, UIO_USERSPACE, uap->link, p); - if (vp->v_type == VDIR) - nd.ni_cnd.cn_flags |= WILLBEDIR; error = namei(&nd); if (!error) { if (nd.ni_vp != NULL) { @@ -990,10 +989,13 @@ unlink(p, uap, retval) LEASE_CHECK(vp, p, p->p_ucred, LEASE_WRITE); VOP_LOCK(vp); - if (vp->v_type != VDIR || - (error = suser(p->p_ucred, &p->p_acflag)) == 0) { + if (vp->v_type == VDIR) + error = EPERM; /* POSIX */ + else { /* * The root of a mounted filesystem cannot be deleted. + * + * XXX: can this only be a VDIR case? */ if (vp->v_flag & VROOT) error = EBUSY; diff --git a/sys/kern/vfs_syscalls.c b/sys/kern/vfs_syscalls.c index ec728b3..95e9de0 100644 --- a/sys/kern/vfs_syscalls.c +++ b/sys/kern/vfs_syscalls.c @@ -36,7 +36,7 @@ * SUCH DAMAGE. * * @(#)vfs_syscalls.c 8.13 (Berkeley) 4/15/94 - * $Id: vfs_syscalls.c,v 1.46 1996/01/16 13:07:14 davidg Exp $ + * $Id: vfs_syscalls.c,v 1.47 1996/05/11 04:39:53 bde Exp $ */ /* @@ -886,11 +886,10 @@ link(p, uap, retval) if (error) return (error); vp = nd.ni_vp; - if (vp->v_type != VDIR || - (error = suser(p->p_ucred, &p->p_acflag)) == 0) { + if (vp->v_type == VDIR) + error = EPERM; /* POSIX */ + else { NDINIT(&nd, CREATE, LOCKPARENT, UIO_USERSPACE, uap->link, p); - if (vp->v_type == VDIR) - nd.ni_cnd.cn_flags |= WILLBEDIR; error = namei(&nd); if (!error) { if (nd.ni_vp != NULL) { @@ -990,10 +989,13 @@ unlink(p, uap, retval) LEASE_CHECK(vp, p, p->p_ucred, LEASE_WRITE); VOP_LOCK(vp); - if (vp->v_type != VDIR || - (error = suser(p->p_ucred, &p->p_acflag)) == 0) { + if (vp->v_type == VDIR) + error = EPERM; /* POSIX */ + else { /* * The root of a mounted filesystem cannot be deleted. + * + * XXX: can this only be a VDIR case? */ if (vp->v_flag & VROOT) error = EBUSY; |