diff options
author | kib <kib@FreeBSD.org> | 2009-09-06 11:44:46 +0000 |
---|---|---|
committer | kib <kib@FreeBSD.org> | 2009-09-06 11:44:46 +0000 |
commit | 14578a32762c68f2642b1efa67688539a49d1042 (patch) | |
tree | 2d45ff70a2b01b2b1f028949185e7003e0ab231e /sys/kern/vfs_syscalls.c | |
parent | 73faea23017b4ce65aa723109ce740c5dacc3dc1 (diff) | |
download | FreeBSD-src-14578a32762c68f2642b1efa67688539a49d1042.zip FreeBSD-src-14578a32762c68f2642b1efa67688539a49d1042.tar.gz |
In fhopen, vfs_ref() the mount point while vnode is unlocked, to prevent
vn_start_write(NULL, &mp) from operating on potentially freed or reused
struct mount *.
Remove unmatched vfs_rel() in cleanup.
Noted and reviewed by: tegge
Tested by: pho
MFC after: 3 days
Diffstat (limited to 'sys/kern/vfs_syscalls.c')
-rw-r--r-- | sys/kern/vfs_syscalls.c | 4 |
1 files changed, 3 insertions, 1 deletions
diff --git a/sys/kern/vfs_syscalls.c b/sys/kern/vfs_syscalls.c index ed7f999..0a8ef46 100644 --- a/sys/kern/vfs_syscalls.c +++ b/sys/kern/vfs_syscalls.c @@ -4439,12 +4439,15 @@ fhopen(td, uap) goto bad; } if (fmode & O_TRUNC) { + vfs_ref(mp); VOP_UNLOCK(vp, 0); /* XXX */ if ((error = vn_start_write(NULL, &mp, V_WAIT | PCATCH)) != 0) { vrele(vp); + vfs_rel(mp); goto out; } vn_lock(vp, LK_EXCLUSIVE | LK_RETRY); /* XXX */ + vfs_rel(mp); #ifdef MAC /* * We don't yet have fp->f_cred, so use td->td_ucred, which @@ -4516,7 +4519,6 @@ fhopen(td, uap) VOP_UNLOCK(vp, 0); fdrop(fp, td); - vfs_rel(mp); VFS_UNLOCK_GIANT(vfslocked); td->td_retval[0] = indx; return (0); |