@@ -1,7 +1,7 @@
# SPDX-License-Identifier: GPL-2.0-only
obj-$(CONFIG_EROFS_FS) += erofs.o
-erofs-objs := super.o inode.o data.o namei.o dir.o utils.o pcpubuf.o
+erofs-objs := super.o inode.o data.o namei.o dir.o utils.o pcpubuf.o fscache.o
erofs-$(CONFIG_EROFS_FS_XATTR) += xattr.o
erofs-$(CONFIG_EROFS_FS_ZIP) += decompressor.o zmap.o zdata.o
erofs-$(CONFIG_EROFS_FS_ZIP_LZMA) += decompressor_lzma.o
new file mode 100644
@@ -0,0 +1,37 @@
+#include "internal.h"
+
+int erofs_fscache_init(struct erofs_sb_info *sbi, char *bootstrap_path)
+{
+ sbi->volume = fscache_acquire_volume("erofs", NULL, 0);
+ if (!sbi->volume) {
+ printk("fscache_acquire_volume() failed\n");
+ return -EINVAL;
+ }
+
+ /*
+ * TODO: @object_size is 0 since erofs can not get size of bootstrap
+ * file.
+ */
+ sbi->bootstrap = fscache_acquire_cookie(sbi->volume, 0,
+ bootstrap_path, strlen(bootstrap_path),
+ NULL, 0,
+ 1 /*TODO: we don't want FSCACHE_COOKIE_NO_DATA_TO_READ set */
+ );
+
+ if (!sbi->bootstrap) {
+ printk("fscache_acquire_cookie() for bootstrap failed\n");
+ /* cleanup for sbi->volume is delayed to erofs_fscache_cleanup() */
+ return -EINVAL;
+ }
+
+ fscache_use_cookie(sbi->bootstrap, false);
+
+ return 0;
+}
+
+void erofs_fscache_cleanup(struct erofs_sb_info *sbi)
+{
+ fscache_unuse_cookie(sbi->bootstrap, NULL, NULL);
+ fscache_relinquish_cookie(sbi->bootstrap, false);
+ fscache_relinquish_volume(sbi->volume, 0, false);
+}
@@ -17,6 +17,7 @@
#include <linux/slab.h>
#include <linux/vmalloc.h>
#include <linux/iomap.h>
+#include <linux/fscache.h>
#include "erofs_fs.h"
/* redefine pr_fmt "erofs: " */
@@ -106,6 +107,9 @@ struct erofs_sb_info {
/* pseudo inode to manage cached pages */
struct inode *managed_cache;
+ struct fscache_volume *volume;
+ struct fscache_cookie *bootstrap;
+
struct erofs_sb_lz4_info lz4;
#endif /* CONFIG_EROFS_FS_ZIP */
struct erofs_dev_context *devs;
@@ -569,6 +573,10 @@ static inline int z_erofs_load_lzma_config(struct super_block *sb,
}
#endif /* !CONFIG_EROFS_FS_ZIP */
+/* fscache.c */
+int erofs_fscache_init(struct erofs_sb_info *sbi, char *bootstrap_path);
+void erofs_fscache_cleanup(struct erofs_sb_info *sbi);
+
#define EFSCORRUPTED EUCLEAN /* Filesystem is corrupted */
#endif /* __EROFS_INTERNAL_H */
@@ -665,6 +665,10 @@ static int erofs_fc_fill_super(struct super_block *sb, struct fs_context *fc)
else
sbi->dax_dev = NULL;
+ err = erofs_fscache_init(sbi, ctx->opt.bootstrap_path);
+ if (err)
+ return err;
+
err = erofs_read_superblock(sb);
if (err)
return err;
@@ -823,6 +827,7 @@ static void erofs_kill_sb(struct super_block *sb)
erofs_free_dev_context(sbi->devs);
fs_put_dax(sbi->dax_dev);
+ erofs_fscache_cleanup(sbi);
kfree(sbi);
sb->s_fs_info = NULL;
}
This patch only handles the volume cookie and data file cookie for bootstrap. The corresponding IO path is remained to be implemented in the following patch. Signed-off-by: Jeffle Xu <jefflexu@linux.alibaba.com> --- fs/erofs/Makefile | 2 +- fs/erofs/fscache.c | 37 +++++++++++++++++++++++++++++++++++++ fs/erofs/internal.h | 8 ++++++++ fs/erofs/super.c | 5 +++++ 4 files changed, 51 insertions(+), 1 deletion(-) create mode 100644 fs/erofs/fscache.c