[PATCH v2 resend] erofs: make filesystem exportable

Gao Xiang hsiangkao at linux.alibaba.com
Tue Apr 26 14:45:55 AEST 2022


On Mon, Apr 25, 2022 at 12:07:12PM +0800, Hongnan Li wrote:
> Implement export operations in order to make EROFS support accessing
> inodes with filehandles so that it can be exported via NFS and used
> by overlayfs.
> 
> Without this patch, 'exportfs -rv' will report:
> exportfs: /root/erofs_mp does not support NFS export
> 
> Also tested with unionmount-testsuite and the testcase below passes now:
> ./run --ov --erofs --verify hard-link
> 
> For more details about the testcase, see:
> https://github.com/amir73il/unionmount-testsuite/pull/6
> 
> Signed-off-by: Hongnan Li <hongnan.li at linux.alibaba.com>
> ---
>  fs/erofs/internal.h |  2 +-
>  fs/erofs/namei.c    |  5 ++---
>  fs/erofs/super.c    | 40 ++++++++++++++++++++++++++++++++++++++++
>  3 files changed, 43 insertions(+), 4 deletions(-)
> 
> diff --git a/fs/erofs/internal.h b/fs/erofs/internal.h
> index 5298c4ee277d..12c65f647324 100644
> --- a/fs/erofs/internal.h
> +++ b/fs/erofs/internal.h
> @@ -509,7 +509,7 @@ int erofs_getattr(struct user_namespace *mnt_userns, const struct path *path,
>  /* namei.c */
>  extern const struct inode_operations erofs_dir_iops;
>  
> -int erofs_namei(struct inode *dir, struct qstr *name,
> +int erofs_namei(struct inode *dir, const struct qstr *name,
>  		erofs_nid_t *nid, unsigned int *d_type);
>  
>  /* dir.c */
> diff --git a/fs/erofs/namei.c b/fs/erofs/namei.c
> index 554efa363317..fd75506799c4 100644
> --- a/fs/erofs/namei.c
> +++ b/fs/erofs/namei.c
> @@ -165,9 +165,8 @@ static void *find_target_block_classic(struct erofs_buf *target,
>  	return candidate;
>  }
>  
> -int erofs_namei(struct inode *dir,
> -		struct qstr *name,
> -		erofs_nid_t *nid, unsigned int *d_type)
> +int erofs_namei(struct inode *dir, const struct qstr *name, erofs_nid_t *nid,
> +		unsigned int *d_type)
>  {
>  	int ndirents;
>  	struct erofs_buf buf = __EROFS_BUF_INITIALIZER;
> diff --git a/fs/erofs/super.c b/fs/erofs/super.c
> index 0c4b41130c2f..1c77b7acabd0 100644
> --- a/fs/erofs/super.c
> +++ b/fs/erofs/super.c
> @@ -13,6 +13,7 @@
>  #include <linux/fs_context.h>
>  #include <linux/fs_parser.h>
>  #include <linux/dax.h>
> +#include <linux/exportfs.h>
>  #include "xattr.h"
>  
>  #define CREATE_TRACE_POINTS
> @@ -577,6 +578,44 @@ static int erofs_init_managed_cache(struct super_block *sb)
>  static int erofs_init_managed_cache(struct super_block *sb) { return 0; }
>  #endif
>  
> +static struct inode *erofs_nfs_get_inode(struct super_block *sb,
> +		u64 ino, u32 generation)
> +{
> +	return erofs_iget(sb, ino, false);
> +}
> +
> +static struct dentry *erofs_fh_to_dentry(struct super_block *sb, struct fid *fid,
> +		int fh_len, int fh_type)
> +{
> +	return generic_fh_to_dentry(sb, fid, fh_len, fh_type,
> +				    erofs_nfs_get_inode);
> +}
> +
> +static struct dentry *erofs_fh_to_parent(struct super_block *sb, struct fid *fid,
> +		int fh_len, int fh_type)
> +{
> +	return generic_fh_to_parent(sb, fid, fh_len, fh_type,
> +				    erofs_nfs_get_inode);
> +}
> +
> +static struct dentry *erofs_get_parent(struct dentry *child)
> +{
> +	erofs_nid_t nid;
> +	unsigned int d_type;
> +	int err;
> +
> +	err = erofs_namei(d_inode(child), &dotdot_name, &nid, &d_type);
> +	if (err)
> +		return ERR_PTR(err);
> +	return d_obtain_alias(erofs_iget(child->d_sb, nid, d_type == FT_DIR));
> +}
> +
> +static const struct export_operations erofs_export_ops = {
> +	.fh_to_dentry = erofs_fh_to_dentry,
> +	.fh_to_parent = erofs_fh_to_parent,
> +	.get_parent = erofs_get_parent,
> +};
> +
>  static int erofs_fc_fill_super(struct super_block *sb, struct fs_context *fc)
>  {
>  	struct inode *inode;
> @@ -618,6 +657,7 @@ static int erofs_fc_fill_super(struct super_block *sb, struct fs_context *fc)
>  	sb->s_time_gran = 1;
>  
>  	sb->s_op = &erofs_sops;
> +	sb->s_export_op = &erofs_export_ops;

I might need to rearrange this part later since it has a slight conflict
with the fscache patchset. Otherwise looks good to me,

Reviewed-by: Gao Xiang <hsiangkao at linux.alibaba.com>

Thanks,
Gao Xiang

>  	sb->s_xattr = erofs_xattr_handlers;
>  
>  	if (test_opt(&sbi->opt, POSIX_ACL))
> -- 
> 2.19.1.6.gb485710b


More information about the Linux-erofs mailing list