Re: [PATCH] mm/zswap: use workqueue to destroy pool

From: Sergey Senozhatsky
Date: Thu Apr 28 2016 - 00:08:22 EST


On (04/28/16 10:40), Sergey Senozhatsky wrote:
[..]
> the bigger issue here (and I was thinking at some point of fixing it,
> but then I grepped to see how many API users are in there, and I gave
> up) is that it seems we have no way to check if the dir exists in debugfs.

well, unless we want to do something like below. but I don't think Greg
will not buy it and the basic rule is to be careful in the driver code
and avoid any collisions.

---

fs/debugfs/inode.c | 48 ++++++++++++++++++++++++++++++++++++++++++++++++
include/linux/debugfs.h | 7 +++++++
2 files changed, 55 insertions(+)

diff --git a/fs/debugfs/inode.c b/fs/debugfs/inode.c
index 8580831..76cf851 100644
--- a/fs/debugfs/inode.c
+++ b/fs/debugfs/inode.c
@@ -709,6 +709,54 @@ exit:
EXPORT_SYMBOL_GPL(debugfs_rename);

/**
+ * debugfs_entry_exists - lookup file/directory name
+ *
+ * @name: a pointer to a string containing the name of the file/directory
+ * to lookup.
+ * @parent: a pointer to the parent dentry. This should be a directory
+ * dentry if set. If this parameter is NULL, then the root of the
+ * debugfs filesystem will be used.
+ *
+ * This function lookup a file/directory name in debugfs. If the
+ * name corresponds to positive dentry, the function will return %0.
+ *
+ * If debugfs is not enabled in the kernel, the value -%ENODEV will be
+ * returned.
+ */
+int debugfs_entry_exists(const char *name, struct dentry *parent)
+{
+ struct dentry *dentry;
+ int error;
+
+ if (IS_ERR(parent))
+ return PTR_ERR(parent);
+
+ error = simple_pin_fs(&debug_fs_type, &debugfs_mount,
+ &debugfs_mount_count);
+ if (error)
+ return error;
+
+ if (!parent)
+ parent = debugfs_mount->mnt_root;
+
+ error = -EINVAL;
+ inode_lock(d_inode(parent));
+ dentry = lookup_one_len(name, parent, strlen(name));
+ if (IS_ERR(dentry)) {
+ error = PTR_ERR(dentry);
+ } else {
+ if (d_really_is_positive(dentry))
+ error = 0;
+ dput(dentry);
+ }
+
+ inode_unlock(d_inode(parent));
+ simple_release_fs(&debugfs_mount, &debugfs_mount_count);
+ return error;
+}
+EXPORT_SYMBOL_GPL(debugfs_entry_exists);
+
+/**
* debugfs_initialized - Tells whether debugfs has been registered
*/
bool debugfs_initialized(void)
diff --git a/include/linux/debugfs.h b/include/linux/debugfs.h
index 981e53a..5b6321e 100644
--- a/include/linux/debugfs.h
+++ b/include/linux/debugfs.h
@@ -124,6 +124,8 @@ ssize_t debugfs_read_file_bool(struct file *file, char __user *user_buf,
ssize_t debugfs_write_file_bool(struct file *file, const char __user *user_buf,
size_t count, loff_t *ppos);

+int debugfs_entry_exists(const char *name, struct dentry *parent);
+
#else

#include <linux/err.h>
@@ -312,6 +314,11 @@ static inline ssize_t debugfs_write_file_bool(struct file *file,
return -ENODEV;
}

+static inline int debugfs_entry_exists(const char *name, struct dentry *parent)
+{
+ return -ENODEV;
+}
+
#endif

#endif