summaryrefslogtreecommitdiffstats
path: root/sys/kern/vfs_syscalls.c
diff options
context:
space:
mode:
authorrwatson <rwatson@FreeBSD.org>2003-01-31 21:13:25 +0000
committerrwatson <rwatson@FreeBSD.org>2003-01-31 21:13:25 +0000
commite9e0de5ca49975c9cdbde8a3c003ba0e84e31847 (patch)
treeaa07cf9ac7cda19b1fe705000bbe8793af52d5c0 /sys/kern/vfs_syscalls.c
parent9dd70473b6bcaa295c57599a605acdb94ba8ef9c (diff)
downloadFreeBSD-src-e9e0de5ca49975c9cdbde8a3c003ba0e84e31847.zip
FreeBSD-src-e9e0de5ca49975c9cdbde8a3c003ba0e84e31847.tar.gz
Correct handling of locking for chroot() and chdir() cases: rather
than having change_dir() release the vnode lock on success, hold the lock so that we can use it later when invoking MAC checks and VOP_ACCESS() in the chroot() code. Update the comment to reflect this calling convention. Update callers to unlock the vnode lock. Correct a typo regarding vnode naming in the MAC case that crept in via the previous patch applied.
Diffstat (limited to 'sys/kern/vfs_syscalls.c')
-rw-r--r--sys/kern/vfs_syscalls.c15
1 files changed, 8 insertions, 7 deletions
diff --git a/sys/kern/vfs_syscalls.c b/sys/kern/vfs_syscalls.c
index 3752f0c..b78d545 100644
--- a/sys/kern/vfs_syscalls.c
+++ b/sys/kern/vfs_syscalls.c
@@ -465,6 +465,7 @@ kern_chdir(struct thread *td, char *path, enum uio_seg pathseg)
NDINIT(&nd, LOOKUP, FOLLOW | LOCKLEAF, pathseg, path, td);
if ((error = change_dir(&nd, td)) != 0)
return (error);
+ VOP_UNLOCK(nd.ni_vp, 0, td);
NDFREE(&nd, NDF_ONLY_PNBUF);
FILEDESC_LOCK(fdp);
vp = fdp->fd_cdir;
@@ -543,10 +544,11 @@ chroot(td, uap)
goto error;
#ifdef MAC
if ((error = mac_check_vnode_chroot(td->td_ucred, nd.ni_vp))) {
- vput(vp);
+ vput(nd.ni_vp);
goto error;
}
#endif
+ VOP_UNLOCK(nd.ni_vp, 0, td);
FILEDESC_LOCK(fdp);
if (chroot_allow_open_directories == 0 ||
(chroot_allow_open_directories == 1 && fdp->fd_rdir != rootvnode)) {
@@ -574,7 +576,8 @@ error:
}
/*
- * Common routine for chroot and chdir.
+ * Common routine for chroot and chdir. On success, the directory vnode
+ * is returned locked, and must be unlocked by the caller.
*/
static int
change_dir(ndp, td)
@@ -591,15 +594,13 @@ change_dir(ndp, td)
if (vp->v_type != VDIR)
error = ENOTDIR;
#ifdef MAC
- else if ((error = mac_check_vnode_chdir(td->td_ucred, vp)) != 0) {
- }
+ if (error == 0)
+ error = mac_check_vnode_chdir(td->td_ucred, vp);
#endif
- else
+ if (error == 0)
error = VOP_ACCESS(vp, VEXEC, td->td_ucred, td);
if (error)
vput(vp);
- else
- VOP_UNLOCK(vp, 0, td);
return (error);
}
OpenPOWER on IntegriCloud