[Devel] [PATCH 2/7] mnt_ns: introduce global list of mount namespaces for debug
Alexander Mikhalitsyn
alexander.mikhalitsyn at virtuozzo.com
Wed Jun 2 18:59:31 MSK 2021
From: Konstantin Khorenko <khorenko at virtuozzo.com>
We've got several cases when ploop could not be unmounted resulting in
-EBUSY. Sometimes we could find what holds it sometimes not, so let's
introduce the global list of mount namespaces: it will make it easier to
debug such cases.
https://jira.sw.ru/browse/PSBM-80869
Signed-off-by: Konstantin Khorenko <khorenko at virtuozzo.com>
Reviewed-by: Andrey Ryabinin <aryabinin at virtuozzo.com>
(cherry picked from commit abee9d40a8d159ece11594b77fb6f5b473359cfa)
VZ 8 rebase part https://jira.sw.ru/browse/PSBM-127837
Signed-off-by: Alexander Mikhalitsyn <alexander.mikhalitsyn at virtuozzo.com>
---
fs/mount.h | 1 +
fs/namespace.c | 14 ++++++++++++++
2 files changed, 15 insertions(+)
diff --git a/fs/mount.h b/fs/mount.h
index e3e0379d5c47..9225fc7bce30 100644
--- a/fs/mount.h
+++ b/fs/mount.h
@@ -17,6 +17,7 @@ struct mnt_namespace {
u64 event;
unsigned int mounts; /* # of mounts in the namespace */
unsigned int pending_mounts;
+ struct list_head mntns_list;
} __randomize_layout;
struct mnt_pcp {
diff --git a/fs/namespace.c b/fs/namespace.c
index 6bace551d08a..b721c0569c32 100644
--- a/fs/namespace.c
+++ b/fs/namespace.c
@@ -3263,6 +3263,10 @@ static void free_mnt_ns(struct mnt_namespace *ns)
ns_free_inum(&ns->ns);
dec_mnt_namespaces(ns->ucounts);
put_user_ns(ns->user_ns);
+
+ namespace_lock();
+ list_del(&ns->mntns_list);
+ namespace_unlock();
kfree(ns);
}
@@ -3274,6 +3278,7 @@ static void free_mnt_ns(struct mnt_namespace *ns)
* is effectively never, so we can ignore the possibility.
*/
static atomic64_t mnt_ns_seq = ATOMIC64_INIT(1);
+static LIST_HEAD(all_mntns_list); /* protected by namespace_sem */
static struct mnt_namespace *alloc_mnt_ns(struct user_namespace *user_ns, bool anon)
{
@@ -3303,6 +3308,7 @@ static struct mnt_namespace *alloc_mnt_ns(struct user_namespace *user_ns, bool a
new_ns->seq = atomic64_add_return(1, &mnt_ns_seq);
atomic_set(&new_ns->count, 1);
INIT_LIST_HEAD(&new_ns->list);
+ INIT_LIST_HEAD(&new_ns->mntns_list);
init_waitqueue_head(&new_ns->poll);
new_ns->user_ns = get_user_ns(user_ns);
new_ns->ucounts = ucounts;
@@ -3334,6 +3340,8 @@ struct mnt_namespace *copy_mnt_ns(unsigned long flags, struct mnt_namespace *ns,
return new_ns;
namespace_lock();
+ list_add_tail(&new_ns->mntns_list, &all_mntns_list);
+
/* First pass: copy the tree topology */
copy_flags = CL_COPY_UNBINDABLE | CL_EXPIRE;
if (user_ns != ns->user_ns)
@@ -3401,6 +3409,9 @@ struct dentry *mount_subtree(struct vfsmount *m, const char *name)
ns->root = mnt;
ns->mounts++;
list_add(&mnt->mnt_list, &ns->list);
+ namespace_lock();
+ list_add_tail(&ns->mntns_list, &all_mntns_list);
+ namespace_unlock();
err = vfs_path_lookup(m->mnt_root, m,
name, LOOKUP_FOLLOW|LOOKUP_AUTOMOUNT, &path);
@@ -3692,6 +3703,9 @@ static void __init init_mount_tree(void)
ns->root = m;
ns->mounts = 1;
list_add(&m->mnt_list, &ns->list);
+ namespace_lock();
+ list_add_tail(&ns->mntns_list, &all_mntns_list);
+ namespace_unlock();
init_task.nsproxy->mnt_ns = ns;
get_mnt_ns(ns);
--
2.28.0
More information about the Devel
mailing list