Skip to content

Commit

Permalink
take unlazy_walk() into umount_lookup_last()
Browse files Browse the repository at this point in the history
... and massage it a bit to reduce nesting

Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
  • Loading branch information
Al Viro committed Sep 9, 2013
1 parent 4e10f3c commit 3575952
Showing 1 changed file with 27 additions and 33 deletions.
60 changes: 27 additions & 33 deletions fs/namei.c
Original file line number Diff line number Diff line change
Expand Up @@ -2256,19 +2256,22 @@ umount_lookup_last(struct nameidata *nd, struct path *path)
struct dentry *dentry;
struct dentry *dir = nd->path.dentry;

if (unlikely(nd->flags & LOOKUP_RCU)) {
WARN_ON_ONCE(1);
error = -ECHILD;
goto error_check;
/* If we're in rcuwalk, drop out of it to handle last component */
if (nd->flags & LOOKUP_RCU) {
if (unlazy_walk(nd, NULL)) {
error = -ECHILD;
goto out;
}
}

nd->flags &= ~LOOKUP_PARENT;

if (unlikely(nd->last_type != LAST_NORM)) {
error = handle_dots(nd, nd->last_type);
if (!error)
dentry = dget(nd->path.dentry);
goto error_check;
if (error)
goto out;
dentry = dget(nd->path.dentry);
goto done;
}

mutex_lock(&dir->d_inode->i_mutex);
Expand All @@ -2282,28 +2285,28 @@ umount_lookup_last(struct nameidata *nd, struct path *path)
dentry = d_alloc(dir, &nd->last);
if (!dentry) {
error = -ENOMEM;
} else {
dentry = lookup_real(dir->d_inode, dentry, nd->flags);
if (IS_ERR(dentry))
error = PTR_ERR(dentry);
goto out;
}
dentry = lookup_real(dir->d_inode, dentry, nd->flags);
error = PTR_ERR(dentry);
if (IS_ERR(dentry))
goto out;
}
mutex_unlock(&dir->d_inode->i_mutex);

error_check:
if (!error) {
if (!dentry->d_inode) {
error = -ENOENT;
dput(dentry);
} else {
path->dentry = dentry;
path->mnt = mntget(nd->path.mnt);
if (should_follow_link(dentry->d_inode,
nd->flags & LOOKUP_FOLLOW))
return 1;
follow_mount(path);
}
done:
if (!dentry->d_inode) {
error = -ENOENT;
dput(dentry);
goto out;
}
path->dentry = dentry;
path->mnt = mntget(nd->path.mnt);
if (should_follow_link(dentry->d_inode, nd->flags & LOOKUP_FOLLOW))
return 1;
follow_mount(path);
error = 0;
out:
terminate_walk(nd);
return error;
}
Expand Down Expand Up @@ -2334,15 +2337,6 @@ path_umountat(int dfd, const char *name, struct path *path, unsigned int flags)
if (err)
goto out;

/* If we're in rcuwalk, drop out of it to handle last component */
if (nd.flags & LOOKUP_RCU) {
err = unlazy_walk(&nd, NULL);
if (err) {
terminate_walk(&nd);
goto out;
}
}

err = umount_lookup_last(&nd, path);
while (err > 0) {
void *cookie;
Expand Down

0 comments on commit 3575952

Please sign in to comment.