Commit cd140ce9 authored by Hongbo Li's avatar Hongbo Li Committed by Christian Brauner

hostfs: convert hostfs to use the new mount API

Convert the hostfs filesystem to the new internal mount API as the old
one will be obsoleted and removed.  This allows greater flexibility in
communication of mount parameters between userspace, the VFS and the
filesystem.

See Documentation/filesystems/mount_api.txt for more information.
Signed-off-by: default avatarHongbo Li <lihongbo22@huawei.com>
Link: https://lore.kernel.org/r/20240530120111.3794664-1-lihongbo22@huawei.comSigned-off-by: default avatarChristian Brauner <brauner@kernel.org>
parent 1613e604
...@@ -16,11 +16,16 @@ ...@@ -16,11 +16,16 @@
#include <linux/seq_file.h> #include <linux/seq_file.h>
#include <linux/writeback.h> #include <linux/writeback.h>
#include <linux/mount.h> #include <linux/mount.h>
#include <linux/fs_context.h>
#include <linux/namei.h> #include <linux/namei.h>
#include "hostfs.h" #include "hostfs.h"
#include <init.h> #include <init.h>
#include <kern.h> #include <kern.h>
struct hostfs_fs_info {
char *host_root_path;
};
struct hostfs_inode_info { struct hostfs_inode_info {
int fd; int fd;
fmode_t mode; fmode_t mode;
...@@ -90,8 +95,10 @@ static char *__dentry_name(struct dentry *dentry, char *name) ...@@ -90,8 +95,10 @@ static char *__dentry_name(struct dentry *dentry, char *name)
char *p = dentry_path_raw(dentry, name, PATH_MAX); char *p = dentry_path_raw(dentry, name, PATH_MAX);
char *root; char *root;
size_t len; size_t len;
struct hostfs_fs_info *fsi;
root = dentry->d_sb->s_fs_info; fsi = dentry->d_sb->s_fs_info;
root = fsi->host_root_path;
len = strlen(root); len = strlen(root);
if (IS_ERR(p)) { if (IS_ERR(p)) {
__putname(name); __putname(name);
...@@ -196,8 +203,10 @@ static int hostfs_statfs(struct dentry *dentry, struct kstatfs *sf) ...@@ -196,8 +203,10 @@ static int hostfs_statfs(struct dentry *dentry, struct kstatfs *sf)
long long f_bavail; long long f_bavail;
long long f_files; long long f_files;
long long f_ffree; long long f_ffree;
struct hostfs_fs_info *fsi;
err = do_statfs(dentry->d_sb->s_fs_info, fsi = dentry->d_sb->s_fs_info;
err = do_statfs(fsi->host_root_path,
&sf->f_bsize, &f_blocks, &f_bfree, &f_bavail, &f_files, &sf->f_bsize, &f_blocks, &f_bfree, &f_bavail, &f_files,
&f_ffree, &sf->f_fsid, sizeof(sf->f_fsid), &f_ffree, &sf->f_fsid, sizeof(sf->f_fsid),
&sf->f_namelen); &sf->f_namelen);
...@@ -245,7 +254,11 @@ static void hostfs_free_inode(struct inode *inode) ...@@ -245,7 +254,11 @@ static void hostfs_free_inode(struct inode *inode)
static int hostfs_show_options(struct seq_file *seq, struct dentry *root) static int hostfs_show_options(struct seq_file *seq, struct dentry *root)
{ {
const char *root_path = root->d_sb->s_fs_info; struct hostfs_fs_info *fsi;
const char *root_path;
fsi = root->d_sb->s_fs_info;
root_path = fsi->host_root_path;
size_t offset = strlen(root_ino) + 1; size_t offset = strlen(root_ino) + 1;
if (strlen(root_path) > offset) if (strlen(root_path) > offset)
...@@ -922,10 +935,11 @@ static const struct inode_operations hostfs_link_iops = { ...@@ -922,10 +935,11 @@ static const struct inode_operations hostfs_link_iops = {
.get_link = hostfs_get_link, .get_link = hostfs_get_link,
}; };
static int hostfs_fill_sb_common(struct super_block *sb, void *d, int silent) static int hostfs_fill_super(struct super_block *sb, struct fs_context *fc)
{ {
struct hostfs_fs_info *fsi = sb->s_fs_info;
struct inode *root_inode; struct inode *root_inode;
char *host_root_path, *req_root = d; char *host_root = fc->source;
int err; int err;
sb->s_blocksize = 1024; sb->s_blocksize = 1024;
...@@ -939,15 +953,15 @@ static int hostfs_fill_sb_common(struct super_block *sb, void *d, int silent) ...@@ -939,15 +953,15 @@ static int hostfs_fill_sb_common(struct super_block *sb, void *d, int silent)
return err; return err;
/* NULL is printed as '(null)' by printf(): avoid that. */ /* NULL is printed as '(null)' by printf(): avoid that. */
if (req_root == NULL) if (fc->source == NULL)
req_root = ""; host_root = "";
sb->s_fs_info = host_root_path = fsi->host_root_path =
kasprintf(GFP_KERNEL, "%s/%s", root_ino, req_root); kasprintf(GFP_KERNEL, "%s/%s", root_ino, host_root);
if (host_root_path == NULL) if (fsi->host_root_path == NULL)
return -ENOMEM; return -ENOMEM;
root_inode = hostfs_iget(sb, host_root_path); root_inode = hostfs_iget(sb, fsi->host_root_path);
if (IS_ERR(root_inode)) if (IS_ERR(root_inode))
return PTR_ERR(root_inode); return PTR_ERR(root_inode);
...@@ -955,7 +969,7 @@ static int hostfs_fill_sb_common(struct super_block *sb, void *d, int silent) ...@@ -955,7 +969,7 @@ static int hostfs_fill_sb_common(struct super_block *sb, void *d, int silent)
char *name; char *name;
iput(root_inode); iput(root_inode);
name = follow_link(host_root_path); name = follow_link(fsi->host_root_path);
if (IS_ERR(name)) if (IS_ERR(name))
return PTR_ERR(name); return PTR_ERR(name);
...@@ -972,11 +986,38 @@ static int hostfs_fill_sb_common(struct super_block *sb, void *d, int silent) ...@@ -972,11 +986,38 @@ static int hostfs_fill_sb_common(struct super_block *sb, void *d, int silent)
return 0; return 0;
} }
static struct dentry *hostfs_read_sb(struct file_system_type *type, static int hostfs_fc_get_tree(struct fs_context *fc)
int flags, const char *dev_name,
void *data)
{ {
return mount_nodev(type, flags, data, hostfs_fill_sb_common); return get_tree_nodev(fc, hostfs_fill_super);
}
static void hostfs_fc_free(struct fs_context *fc)
{
struct hostfs_fs_info *fsi = fc->s_fs_info;
if (!fsi)
return;
kfree(fsi->host_root_path);
kfree(fsi);
}
static const struct fs_context_operations hostfs_context_ops = {
.get_tree = hostfs_fc_get_tree,
.free = hostfs_fc_free,
};
static int hostfs_init_fs_context(struct fs_context *fc)
{
struct hostfs_fs_info *fsi;
fsi = kzalloc(sizeof(*fsi), GFP_KERNEL);
if (!fsi)
return -ENOMEM;
fc->s_fs_info = fsi;
fc->ops = &hostfs_context_ops;
return 0;
} }
static void hostfs_kill_sb(struct super_block *s) static void hostfs_kill_sb(struct super_block *s)
...@@ -988,7 +1029,7 @@ static void hostfs_kill_sb(struct super_block *s) ...@@ -988,7 +1029,7 @@ static void hostfs_kill_sb(struct super_block *s)
static struct file_system_type hostfs_type = { static struct file_system_type hostfs_type = {
.owner = THIS_MODULE, .owner = THIS_MODULE,
.name = "hostfs", .name = "hostfs",
.mount = hostfs_read_sb, .init_fs_context = hostfs_init_fs_context,
.kill_sb = hostfs_kill_sb, .kill_sb = hostfs_kill_sb,
.fs_flags = 0, .fs_flags = 0,
}; };
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment