vfs: spread struct mount - attach_recursive_mnt
Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
This commit is contained in:
parent
4b8b21f4fe
commit
0fb54e5056
1 changed files with 14 additions and 11 deletions
|
@ -1587,7 +1587,7 @@ static int invent_group_ids(struct mount *mnt, bool recurse)
|
||||||
* Must be called without spinlocks held, since this function can sleep
|
* Must be called without spinlocks held, since this function can sleep
|
||||||
* in allocations.
|
* in allocations.
|
||||||
*/
|
*/
|
||||||
static int attach_recursive_mnt(struct vfsmount *source_mnt,
|
static int attach_recursive_mnt(struct mount *source_mnt,
|
||||||
struct path *path, struct path *parent_path)
|
struct path *path, struct path *parent_path)
|
||||||
{
|
{
|
||||||
LIST_HEAD(tree_list);
|
LIST_HEAD(tree_list);
|
||||||
|
@ -1597,27 +1597,27 @@ static int attach_recursive_mnt(struct vfsmount *source_mnt,
|
||||||
int err;
|
int err;
|
||||||
|
|
||||||
if (IS_MNT_SHARED(dest_mnt)) {
|
if (IS_MNT_SHARED(dest_mnt)) {
|
||||||
err = invent_group_ids(real_mount(source_mnt), true);
|
err = invent_group_ids(source_mnt, true);
|
||||||
if (err)
|
if (err)
|
||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
err = propagate_mnt(dest_mnt, dest_dentry, source_mnt, &tree_list);
|
err = propagate_mnt(dest_mnt, dest_dentry, &source_mnt->mnt, &tree_list);
|
||||||
if (err)
|
if (err)
|
||||||
goto out_cleanup_ids;
|
goto out_cleanup_ids;
|
||||||
|
|
||||||
br_write_lock(vfsmount_lock);
|
br_write_lock(vfsmount_lock);
|
||||||
|
|
||||||
if (IS_MNT_SHARED(dest_mnt)) {
|
if (IS_MNT_SHARED(dest_mnt)) {
|
||||||
for (p = real_mount(source_mnt); p; p = next_mnt(p, source_mnt))
|
for (p = source_mnt; p; p = next_mnt(p, &source_mnt->mnt))
|
||||||
set_mnt_shared(&p->mnt);
|
set_mnt_shared(&p->mnt);
|
||||||
}
|
}
|
||||||
if (parent_path) {
|
if (parent_path) {
|
||||||
detach_mnt(real_mount(source_mnt), parent_path);
|
detach_mnt(source_mnt, parent_path);
|
||||||
attach_mnt(real_mount(source_mnt), path);
|
attach_mnt(source_mnt, path);
|
||||||
touch_mnt_namespace(parent_path->mnt->mnt_ns);
|
touch_mnt_namespace(parent_path->mnt->mnt_ns);
|
||||||
} else {
|
} else {
|
||||||
mnt_set_mountpoint(dest_mnt, dest_dentry, source_mnt);
|
mnt_set_mountpoint(dest_mnt, dest_dentry, &source_mnt->mnt);
|
||||||
commit_tree(real_mount(source_mnt));
|
commit_tree(source_mnt);
|
||||||
}
|
}
|
||||||
|
|
||||||
list_for_each_entry_safe(child, p, &tree_list, mnt.mnt_hash) {
|
list_for_each_entry_safe(child, p, &tree_list, mnt.mnt_hash) {
|
||||||
|
@ -1630,7 +1630,7 @@ static int attach_recursive_mnt(struct vfsmount *source_mnt,
|
||||||
|
|
||||||
out_cleanup_ids:
|
out_cleanup_ids:
|
||||||
if (IS_MNT_SHARED(dest_mnt))
|
if (IS_MNT_SHARED(dest_mnt))
|
||||||
cleanup_group_ids(real_mount(source_mnt), NULL);
|
cleanup_group_ids(source_mnt, NULL);
|
||||||
out:
|
out:
|
||||||
return err;
|
return err;
|
||||||
}
|
}
|
||||||
|
@ -1674,7 +1674,7 @@ static int graft_tree(struct vfsmount *mnt, struct path *path)
|
||||||
if (d_unlinked(path->dentry))
|
if (d_unlinked(path->dentry))
|
||||||
return -ENOENT;
|
return -ENOENT;
|
||||||
|
|
||||||
return attach_recursive_mnt(mnt, path, NULL);
|
return attach_recursive_mnt(real_mount(mnt), path, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -1859,6 +1859,7 @@ static int do_move_mount(struct path *path, char *old_name)
|
||||||
{
|
{
|
||||||
struct path old_path, parent_path;
|
struct path old_path, parent_path;
|
||||||
struct vfsmount *p;
|
struct vfsmount *p;
|
||||||
|
struct mount *old;
|
||||||
int err = 0;
|
int err = 0;
|
||||||
if (!capable(CAP_SYS_ADMIN))
|
if (!capable(CAP_SYS_ADMIN))
|
||||||
return -EPERM;
|
return -EPERM;
|
||||||
|
@ -1883,6 +1884,8 @@ static int do_move_mount(struct path *path, char *old_name)
|
||||||
if (old_path.dentry != old_path.mnt->mnt_root)
|
if (old_path.dentry != old_path.mnt->mnt_root)
|
||||||
goto out1;
|
goto out1;
|
||||||
|
|
||||||
|
old = real_mount(old_path.mnt);
|
||||||
|
|
||||||
if (!mnt_has_parent(old_path.mnt))
|
if (!mnt_has_parent(old_path.mnt))
|
||||||
goto out1;
|
goto out1;
|
||||||
|
|
||||||
|
@ -1906,7 +1909,7 @@ static int do_move_mount(struct path *path, char *old_name)
|
||||||
if (p == old_path.mnt)
|
if (p == old_path.mnt)
|
||||||
goto out1;
|
goto out1;
|
||||||
|
|
||||||
err = attach_recursive_mnt(old_path.mnt, path, &parent_path);
|
err = attach_recursive_mnt(old, path, &parent_path);
|
||||||
if (err)
|
if (err)
|
||||||
goto out1;
|
goto out1;
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue