mirror of https://lore.kernel.org/lkml/
 help / color / mirror / Atom feed
From: Jingbo Xu <jefflexu@linux.alibaba.com>
To: dhowells@redhat.com, linux-cachefs@redhat.com
Cc: linux-kernel@vger.kernel.org, xiang@kernel.org
Subject: [PATCH RFC 2/9] cachefiles: add content map file helpers
Date: Tue,  2 Aug 2022 11:03:35 +0800	[thread overview]
Message-ID: <20220802030342.46302-3-jefflexu@linux.alibaba.com> (raw)
In-Reply-To: <20220802030342.46302-1-jefflexu@linux.alibaba.com>

Besides the mapping mechanism provided by the backing fs, a self
maintained bitmap can be used to track if the corresponding file range
is cached by the backing file or not. In this case, a content map file
is used to permanentize the bitmap.

As the first step, add the helper functions for looking up and freeing
these content map files.

Signed-off-by: Jingbo Xu <jefflexu@linux.alibaba.com>
---
 fs/cachefiles/internal.h |  4 ++
 fs/cachefiles/namei.c    | 88 ++++++++++++++++++++++++++++++++++++++++
 2 files changed, 92 insertions(+)

diff --git a/fs/cachefiles/internal.h b/fs/cachefiles/internal.h
index 6cba2c6de2f9..4c3ee6935811 100644
--- a/fs/cachefiles/internal.h
+++ b/fs/cachefiles/internal.h
@@ -270,6 +270,10 @@ extern struct dentry *cachefiles_get_directory(struct cachefiles_cache *cache,
 					       bool *_is_new);
 extern void cachefiles_put_directory(struct dentry *dir);
 
+int cachefiles_look_up_map(struct cachefiles_cache *cache,
+			   struct dentry *dir, struct file **pfile);
+void cachefiles_put_map(struct file *file);
+
 extern int cachefiles_cull(struct cachefiles_cache *cache, struct dentry *dir,
 			   char *filename);
 
diff --git a/fs/cachefiles/namei.c b/fs/cachefiles/namei.c
index facf2ebe464b..2948eea18ca2 100644
--- a/fs/cachefiles/namei.c
+++ b/fs/cachefiles/namei.c
@@ -231,6 +231,94 @@ void cachefiles_put_directory(struct dentry *dir)
 	}
 }
 
+/*
+ * Look up a content map file.
+ */
+int cachefiles_look_up_map(struct cachefiles_cache *cache,
+			   struct dentry *dir, struct file **pfile)
+{
+	struct dentry *dentry;
+	struct file *file;
+	struct path path;
+	char *name = "Map";
+	int ret;
+
+	inode_lock_nested(d_inode(dir), I_MUTEX_PARENT);
+retry:
+	ret = cachefiles_inject_read_error();
+	if (ret)
+		goto err_unlock_dir;
+
+	dentry = lookup_one_len(name, dir, strlen(name));
+	if (IS_ERR(dentry)) {
+		ret = PTR_ERR(dentry);
+		goto err_unlock_dir;
+	}
+
+	if (d_is_negative(dentry)) {
+		ret = cachefiles_has_space(cache, 1, 0,
+				cachefiles_has_space_for_create);
+		if (ret)
+			goto err_dput;
+
+		ret = vfs_create(&init_user_ns, d_inode(dir), dentry, S_IFREG, true);
+		if (ret)
+			goto err_dput;
+
+		if (unlikely(d_unhashed(dentry))) {
+			cachefiles_put_directory(dentry);
+			goto retry;
+		}
+		ASSERT(d_backing_inode(dentry));
+	}
+
+	inode_lock(d_inode(dentry));
+	inode_unlock(d_inode(dir));
+
+	if (!__cachefiles_mark_inode_in_use(NULL, dentry)) {
+		inode_unlock(d_inode(dentry));
+		dput(dentry);
+		return -EBUSY;
+	}
+
+	inode_unlock(d_inode(dentry));
+	ASSERT(d_backing_inode(dentry));
+
+	if (!d_is_reg(dentry)) {
+		pr_err("%pd is not a file\n", dentry);
+		cachefiles_put_directory(dentry);
+		return -EIO;
+	}
+
+	path.mnt = cache->mnt;
+	path.dentry = dentry;
+	file = open_with_fake_path(&path, O_RDWR | O_LARGEFILE,
+			d_backing_inode(dentry), cache->cache_cred);
+	if (IS_ERR(file))
+		cachefiles_put_directory(dentry);
+
+	*pfile = file;
+	dput(dentry);
+	return 0;
+
+err_dput:
+	dput(dentry);
+err_unlock_dir:
+	inode_unlock(d_inode(dir));
+	return ret;
+}
+
+/*
+ * Put a content map file.
+ */
+void cachefiles_put_map(struct file *file)
+{
+	if (file) {
+		cachefiles_do_unmark_inode_in_use(NULL, file->f_path.dentry);
+		fput(file);
+	}
+}
+
 /*
  * Remove a regular file from the cache.
  */
-- 
2.27.0


  parent reply	other threads:[~2022-08-02  3:04 UTC|newest]

Thread overview: 10+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2022-08-02  3:03 [RFC PATCH 0/9] cachefiles: content map Jingbo Xu
2022-08-02  3:03 ` [PATCH RFC 1/9] cachefiles: improve FSCACHE_COOKIE_NO_DATA_TO_READ optimization Jingbo Xu
2022-08-02  3:03 ` Jingbo Xu [this message]
2022-08-02  3:03 ` [PATCH RFC 3/9] cachefiles: allocate per-subdir content map files Jingbo Xu
2022-08-02  3:03 ` [PATCH RFC 4/9] cachefiles: alloc/load/save content map Jingbo Xu
2022-08-02  3:03 ` [PATCH RFC 5/9] cachefiles: mark content map on write to the backing file Jingbo Xu
2022-08-02  3:03 ` [PATCH RFC 6/9] cachefiles: check content map on read/write Jingbo Xu
2022-08-02  3:03 ` [PATCH RFC 7/9] cachefiles: free content map on invalidate Jingbo Xu
2022-08-02  3:03 ` [PATCH RFC 8/9] cachefiles: resize content map on resize Jingbo Xu
2022-08-02  3:03 ` [PATCH RFC 9/9] cachefiles: cull content map file on cull Jingbo Xu

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20220802030342.46302-3-jefflexu@linux.alibaba.com \
    --to=jefflexu@linux.alibaba.com \
    --cc=dhowells@redhat.com \
    --cc=linux-cachefs@redhat.com \
    --cc=linux-kernel@vger.kernel.org \
    --cc=xiang@kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox

all inboxes | Powered by JetHome®