Skip to content

Commit d561254

Browse files
mihalicynMiklos Szeredi
authored andcommitted
fuse: support idmapped FUSE_EXT_GROUPS
We don't need to remap parent_gid, but have to adjust group membership checks and take idmapping into account. Signed-off-by: Alexander Mikhalitsyn <[email protected]> Signed-off-by: Miklos Szeredi <[email protected]>
1 parent 10dc721 commit d561254

File tree

1 file changed

+12
-7
lines changed

1 file changed

+12
-7
lines changed

fs/fuse/dir.c

Lines changed: 12 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -545,17 +545,21 @@ static u32 fuse_ext_size(size_t size)
545545
/*
546546
* This adds just a single supplementary group that matches the parent's group.
547547
*/
548-
static int get_create_supp_group(struct inode *dir, struct fuse_in_arg *ext)
548+
static int get_create_supp_group(struct mnt_idmap *idmap,
549+
struct inode *dir,
550+
struct fuse_in_arg *ext)
549551
{
550552
struct fuse_conn *fc = get_fuse_conn(dir);
551553
struct fuse_ext_header *xh;
552554
struct fuse_supp_groups *sg;
553555
kgid_t kgid = dir->i_gid;
556+
vfsgid_t vfsgid = make_vfsgid(idmap, fc->user_ns, kgid);
554557
gid_t parent_gid = from_kgid(fc->user_ns, kgid);
558+
555559
u32 sg_len = fuse_ext_size(sizeof(*sg) + sizeof(sg->groups[0]));
556560

557-
if (parent_gid == (gid_t) -1 || gid_eq(kgid, current_fsgid()) ||
558-
!in_group_p(kgid))
561+
if (parent_gid == (gid_t) -1 || vfsgid_eq_kgid(vfsgid, current_fsgid()) ||
562+
!vfsgid_in_group_p(vfsgid))
559563
return 0;
560564

561565
xh = extend_arg(ext, sg_len);
@@ -572,7 +576,8 @@ static int get_create_supp_group(struct inode *dir, struct fuse_in_arg *ext)
572576
return 0;
573577
}
574578

575-
static int get_create_ext(struct fuse_args *args,
579+
static int get_create_ext(struct mnt_idmap *idmap,
580+
struct fuse_args *args,
576581
struct inode *dir, struct dentry *dentry,
577582
umode_t mode)
578583
{
@@ -583,7 +588,7 @@ static int get_create_ext(struct fuse_args *args,
583588
if (fc->init_security)
584589
err = get_security_context(dentry, mode, &ext);
585590
if (!err && fc->create_supp_group)
586-
err = get_create_supp_group(dir, &ext);
591+
err = get_create_supp_group(idmap, dir, &ext);
587592

588593
if (!err && ext.size) {
589594
WARN_ON(args->in_numargs >= ARRAY_SIZE(args->in_args));
@@ -668,7 +673,7 @@ static int fuse_create_open(struct inode *dir, struct dentry *entry,
668673
args.out_args[1].size = sizeof(*outopenp);
669674
args.out_args[1].value = outopenp;
670675

671-
err = get_create_ext(&args, dir, entry, mode);
676+
err = get_create_ext(&nop_mnt_idmap, &args, dir, entry, mode);
672677
if (err)
673678
goto out_free_ff;
674679

@@ -798,7 +803,7 @@ static int create_new_entry(struct fuse_mount *fm, struct fuse_args *args,
798803
args->out_args[0].value = &outarg;
799804

800805
if (args->opcode != FUSE_LINK) {
801-
err = get_create_ext(args, dir, entry, mode);
806+
err = get_create_ext(&nop_mnt_idmap, args, dir, entry, mode);
802807
if (err)
803808
goto out_put_forget_req;
804809
}

0 commit comments

Comments
 (0)