Page Menu
Home
FreeBSD
Search
Configure Global Search
Log In
Files
F144330267
D39767.id120881.diff
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Flag For Later
Award Token
Size
2 KB
Referenced Files
None
Subscribers
None
D39767.id120881.diff
View Options
diff --git a/sys/fs/unionfs/union_subr.c b/sys/fs/unionfs/union_subr.c
--- a/sys/fs/unionfs/union_subr.c
+++ b/sys/fs/unionfs/union_subr.c
@@ -397,13 +397,15 @@
}
if (lowervp != NULL && VN_IS_DOOMED(lowervp)) {
vput(lowervp);
- unp->un_lowervp = NULL;
+ unp->un_lowervp = lowervp = NULL;
}
if (uppervp != NULL && VN_IS_DOOMED(uppervp)) {
vput(uppervp);
- unp->un_uppervp = NULL;
+ unp->un_uppervp = uppervp = NULL;
+ if (lowervp != NULLVP)
+ vp->v_vnlock = lowervp->v_vnlock;
}
- if (unp->un_lowervp == NULL && unp->un_uppervp == NULL) {
+ if (lowervp == NULL && uppervp == NULL) {
unionfs_nodeget_cleanup(vp, unp);
return (ENOENT);
}
diff --git a/sys/fs/unionfs/union_vfsops.c b/sys/fs/unionfs/union_vfsops.c
--- a/sys/fs/unionfs/union_vfsops.c
+++ b/sys/fs/unionfs/union_vfsops.c
@@ -285,8 +285,8 @@
*/
error = unionfs_nodeget(mp, ump->um_uppervp, ump->um_lowervp,
NULLVP, &(ump->um_rootvp), NULL);
- vrele(upperrootvp);
if (error != 0) {
+ vrele(upperrootvp);
free(ump, M_UNIONFSMNT);
mp->mnt_data = NULL;
return (error);
@@ -295,16 +295,30 @@
KASSERT((ump->um_rootvp->v_vflag & VV_ROOT) != 0,
("%s: rootvp without VV_ROOT", __func__));
+ /*
+ * Do not release the namei() reference on upperrootvp until after
+ * we attempt to register the upper mounts. A concurrent unmount
+ * of the upper or lower FS may have caused unionfs_nodeget() to
+ * create a unionfs node with a NULL upper or lower vp and with
+ * no reference held on upperrootvp or lowerrootvp.
+ * vfs_register_upper() should subsequently fail, which is what
+ * we want, but we must ensure neither underlying vnode can be
+ * reused until that happens. We assume the caller holds a reference
+ * to lowerrootvp as it is the mount's covered vnode.
+ */
lowermp = vfs_register_upper_from_vp(ump->um_lowervp, mp,
&ump->um_lower_link);
uppermp = vfs_register_upper_from_vp(ump->um_uppervp, mp,
&ump->um_upper_link);
+ vrele(upperrootvp);
+
if (lowermp == NULL || uppermp == NULL) {
if (lowermp != NULL)
vfs_unregister_upper(lowermp, &ump->um_lower_link);
if (uppermp != NULL)
vfs_unregister_upper(uppermp, &ump->um_upper_link);
+ vflush(mp, 1, FORCECLOSE, curthread);
free(ump, M_UNIONFSMNT);
mp->mnt_data = NULL;
return (ENOENT);
File Metadata
Details
Attached
Mime Type
text/plain
Expires
Sun, Feb 8, 9:27 PM (7 h, 16 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
28499853
Default Alt Text
D39767.id120881.diff (2 KB)
Attached To
Mode
D39767: Various fixes to unionfs error handling logic
Attached
Detach File
Event Timeline
Log In to Comment