From 8b17e540969a0983abe96ffc352397890ab67bf1 Mon Sep 17 00:00:00 2001 From: Mateusz Guzik Date: Sun, 9 Feb 2025 19:55:20 +0100 Subject: [PATCH 1/3] vfs: add initial support for CONFIG_DEBUG_VFS Small collection of macros taken from mmdebug.h Signed-off-by: Mateusz Guzik Link: https://lore.kernel.org/r/20250209185523.745956-2-mjguzik@gmail.com Reviewed-by: Jan Kara Signed-off-by: Christian Brauner --- fs/inode.c | 15 ++++++++++++++ include/linux/fs.h | 1 + include/linux/vfsdebug.h | 45 ++++++++++++++++++++++++++++++++++++++++ lib/Kconfig.debug | 9 ++++++++ 4 files changed, 70 insertions(+) create mode 100644 include/linux/vfsdebug.h diff --git a/fs/inode.c b/fs/inode.c index 5587aabdaa5e..875e66261f06 100644 --- a/fs/inode.c +++ b/fs/inode.c @@ -2953,3 +2953,18 @@ umode_t mode_strip_sgid(struct mnt_idmap *idmap, return mode & ~S_ISGID; } EXPORT_SYMBOL(mode_strip_sgid); + +#ifdef CONFIG_DEBUG_VFS +/* + * Dump an inode. + * + * TODO: add a proper inode dumping routine, this is a stub to get debug off the + * ground. + */ +void dump_inode(struct inode *inode, const char *reason) +{ + pr_warn("%s encountered for inode %px", reason, inode); +} + +EXPORT_SYMBOL(dump_inode); +#endif diff --git a/include/linux/fs.h b/include/linux/fs.h index be3ad155ec9f..d5e3fb14ad8c 100644 --- a/include/linux/fs.h +++ b/include/linux/fs.h @@ -2,6 +2,7 @@ #ifndef _LINUX_FS_H #define _LINUX_FS_H +#include #include #include #include diff --git a/include/linux/vfsdebug.h b/include/linux/vfsdebug.h new file mode 100644 index 000000000000..9cf22d3eb9dd --- /dev/null +++ b/include/linux/vfsdebug.h @@ -0,0 +1,45 @@ +/* SPDX-License-Identifier: GPL-2.0 */ +#ifndef LINUX_VFS_DEBUG_H +#define LINUX_VFS_DEBUG_H 1 + +#include + +struct inode; + +#ifdef CONFIG_DEBUG_VFS +void dump_inode(struct inode *inode, const char *reason); + +#define VFS_BUG_ON(cond) BUG_ON(cond) +#define VFS_WARN_ON(cond) (void)WARN_ON(cond) +#define VFS_WARN_ON_ONCE(cond) (void)WARN_ON_ONCE(cond) +#define VFS_WARN_ONCE(cond, format...) (void)WARN_ONCE(cond, format) +#define VFS_WARN(cond, format...) (void)WARN(cond, format) + +#define VFS_BUG_ON_INODE(cond, inode) ({ \ + if (unlikely(!!(cond))) { \ + dump_inode(inode, "VFS_BUG_ON_INODE(" #cond")");\ + BUG_ON(1); \ + } \ +}) + +#define VFS_WARN_ON_INODE(cond, inode) ({ \ + int __ret_warn = !!(cond); \ + \ + if (unlikely(__ret_warn)) { \ + dump_inode(inode, "VFS_WARN_ON_INODE(" #cond")");\ + WARN_ON(1); \ + } \ + unlikely(__ret_warn); \ +}) +#else +#define VFS_BUG_ON(cond) BUILD_BUG_ON_INVALID(cond) +#define VFS_WARN_ON(cond) BUILD_BUG_ON_INVALID(cond) +#define VFS_WARN_ON_ONCE(cond) BUILD_BUG_ON_INVALID(cond) +#define VFS_WARN_ONCE(cond, format...) BUILD_BUG_ON_INVALID(cond) +#define VFS_WARN(cond, format...) BUILD_BUG_ON_INVALID(cond) + +#define VFS_BUG_ON_INODE(cond, inode) VFS_BUG_ON(cond) +#define VFS_WARN_ON_INODE(cond, inode) BUILD_BUG_ON_INVALID(cond) +#endif /* CONFIG_DEBUG_VFS */ + +#endif diff --git a/lib/Kconfig.debug b/lib/Kconfig.debug index 1af972a92d06..c08ce985c482 100644 --- a/lib/Kconfig.debug +++ b/lib/Kconfig.debug @@ -808,6 +808,15 @@ config ARCH_HAS_DEBUG_VM_PGTABLE An architecture should select this when it can successfully build and run DEBUG_VM_PGTABLE. +config DEBUG_VFS + bool "Debug VFS" + depends on DEBUG_KERNEL + help + Enable this to turn on extended checks in the VFS layer that may impact + performance. + + If unsure, say N. + config DEBUG_VM_IRQSOFF def_bool DEBUG_VM && !PREEMPT_RT From af153bb63a336a7ca0d9c8ef4ca98119c5020030 Mon Sep 17 00:00:00 2001 From: Mateusz Guzik Date: Sun, 9 Feb 2025 19:55:21 +0100 Subject: [PATCH 2/3] vfs: catch invalid modes in may_open() Signed-off-by: Mateusz Guzik Link: https://lore.kernel.org/r/20250209185523.745956-3-mjguzik@gmail.com Reviewed-by: Jan Kara Signed-off-by: Christian Brauner --- fs/namei.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/fs/namei.c b/fs/namei.c index 3ab9440c5b93..21630a0f8e30 100644 --- a/fs/namei.c +++ b/fs/namei.c @@ -3415,6 +3415,8 @@ static int may_open(struct mnt_idmap *idmap, const struct path *path, if ((acc_mode & MAY_EXEC) && path_noexec(path)) return -EACCES; break; + default: + VFS_BUG_ON_INODE(1, inode); } error = inode_permission(idmap, inode, MAY_OPEN | acc_mode); From 3eb7e95104141609d4aed15affadedb81c408f03 Mon Sep 17 00:00:00 2001 From: Mateusz Guzik Date: Sun, 9 Feb 2025 19:55:22 +0100 Subject: [PATCH 3/3] vfs: use the new debug macros in inode_set_cached_link() Signed-off-by: Mateusz Guzik Link: https://lore.kernel.org/r/20250209185523.745956-4-mjguzik@gmail.com Reviewed-by: Jan Kara Signed-off-by: Christian Brauner --- include/linux/fs.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/include/linux/fs.h b/include/linux/fs.h index d5e3fb14ad8c..e71d58c7f59c 100644 --- a/include/linux/fs.h +++ b/include/linux/fs.h @@ -792,6 +792,8 @@ struct inode { static inline void inode_set_cached_link(struct inode *inode, char *link, int linklen) { + VFS_WARN_ON_INODE(strlen(link) != linklen, inode); + VFS_WARN_ON_INODE(inode->i_opflags & IOP_CACHED_LINK, inode); inode->i_link = link; inode->i_linklen = linklen; inode->i_opflags |= IOP_CACHED_LINK;