autofs4: correct offset mount expire check
Ian Kent [Thu, 6 Nov 2008 20:53:22 +0000 (12:53 -0800)]
When checking a directory tree in autofs_tree_busy() we can incorrectly
decide that the tree isn't busy.  This happens for the case of an active
offset mount as autofs4_follow_mount() follows past the active offset
mount, which has an open file handle used for expires, causing the file
handle not to count toward the busyness check.

Signed-off-by: Ian Kent <raven@themaw.net>
Signed-off-by: Jeff Moyer <jmoyer@redhat.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>

fs/autofs4/expire.c

index cde2f8e..4b6fb3f 100644 (file)
@@ -56,12 +56,23 @@ static int autofs4_mount_busy(struct vfsmount *mnt, struct dentry *dentry)
        mntget(mnt);
        dget(dentry);
 
-       if (!autofs4_follow_mount(&mnt, &dentry))
+       if (!follow_down(&mnt, &dentry))
                goto done;
 
-       /* This is an autofs submount, we can't expire it */
-       if (is_autofs4_dentry(dentry))
-               goto done;
+       if (is_autofs4_dentry(dentry)) {
+               struct autofs_sb_info *sbi = autofs4_sbi(dentry->d_sb);
+
+               /* This is an autofs submount, we can't expire it */
+               if (sbi->type == AUTOFS_TYPE_INDIRECT)
+                       goto done;
+
+               /*
+                * Otherwise it's an offset mount and we need to check
+                * if we can umount its mount, if there is one.
+                */
+               if (!d_mountpoint(dentry))
+                       goto done;
+       }
 
        /* Update the expiry counter if fs is busy */
        if (!may_umount_tree(mnt)) {