From: Ashish S. <ash...@or...> - 2014-04-10 01:48:27
|
This patch adds the rootmode=M option to the mount options in fuse library. FUSE user library extracts the octal argument (M) and passes it to the kernel module to set the file permission for root of the mounted filesystem. Signed-off-by: Ashish Samant <ash...@or...> --- lib/mount.c | 23 +++++++++++++++++++++-- util/fusermount.c | 15 +++++++++++++++ 2 files changed, 36 insertions(+), 2 deletions(-) diff --git a/lib/mount.c b/lib/mount.c index fb9231a..aac0d74 100644 --- a/lib/mount.c +++ b/lib/mount.c @@ -69,6 +69,7 @@ struct mount_opts { int nonempty; int auto_unmount; int blkdev; + int rootmode; char *fsname; char *subtype; char *subtype_opt; @@ -87,6 +88,7 @@ static const struct fuse_opt fuse_mount_opts[] = { FUSE_MOUNT_OPT("auto_unmount", auto_unmount), FUSE_MOUNT_OPT("fsname=%s", fsname), FUSE_MOUNT_OPT("subtype=%s", subtype), + FUSE_MOUNT_OPT("rootmode=%o", rootmode), FUSE_OPT_KEY("allow_other", KEY_KERN_OPT), FUSE_OPT_KEY("allow_root", KEY_ALLOW_ROOT), FUSE_OPT_KEY("nonempty", KEY_FUSERMOUNT_OPT), @@ -137,6 +139,7 @@ static void mount_help(void) " -o subtype=NAME set filesystem type\n" " -o large_read issue large read requests (2.4 only)\n" " -o max_read=N set maximum size of read requests\n" +" -o rootmode=M set Root Mode\n" "\n"); } @@ -462,8 +465,8 @@ static int fuse_mount_sys(const char *mnt, struct mount_opts *mo, if (!O_CLOEXEC) fcntl(fd, F_SETFD, FD_CLOEXEC); - snprintf(tmp, sizeof(tmp), "fd=%i,rootmode=%o,user_id=%i,group_id=%i", - fd, stbuf.st_mode & S_IFMT, getuid(), getgid()); + snprintf(tmp, sizeof(tmp), "fd=%i,user_id=%i,group_id=%i", + fd, getuid(), getgid()); res = fuse_opt_add_opt(&mo->kernel_opts, tmp); if (res == -1) @@ -568,9 +571,12 @@ static int get_mnt_flag_opts(char **mnt_optsp, int flags) int fuse_kern_mount(const char *mountpoint, struct fuse_args *args) { + char tmp[128]; struct mount_opts mo; int res = -1; char *mnt_opts = NULL; + int rootmode_value; + struct stat stbuf; memset(&mo, 0, sizeof(mo)); mo.flags = MS_NOSUID | MS_NODEV; @@ -587,6 +593,19 @@ int fuse_kern_mount(const char *mountpoint, struct fuse_args *args) if (mo.ishelp) goto out; + res = stat(mountpoint, &stbuf); + if (res == -1) { + fprintf(stderr , "fuse: failed to access mountpoint %s: %s\n", + mountpoint, strerror(errno)); + return -1; + } + rootmode_value = (stbuf.st_mode & S_IFMT) | mo.rootmode; + snprintf(tmp, sizeof(tmp), "rootmode=%o", rootmode_value); + + res = fuse_opt_add_opt(&mo.kernel_opts, tmp); + if (res == -1) + goto out; + res = -1; if (get_mnt_flag_opts(&mnt_opts, mo.flags) == -1) goto out; diff --git a/util/fusermount.c b/util/fusermount.c index e7dbca6..f6adcf0 100644 --- a/util/fusermount.c +++ b/util/fusermount.c @@ -726,8 +726,10 @@ static int do_mount(const char *mnt, char **typep, mode_t rootmode, char *subtype = NULL; char *source = NULL; char *type = NULL; + char *ref; int check_empty = 1; int blkdev = 0; + int check_rootmode = 0; optbuf = (char *) malloc(strlen(opts) + 128); if (!optbuf) { @@ -739,6 +741,8 @@ static int do_mount(const char *mnt, char **typep, mode_t rootmode, unsigned len; const char *fsname_str = "fsname="; const char *subtype_str = "subtype="; + const char *rootmode_str = "rootmode="; + int rootmode_len = strlen(rootmode_str); for (len = 0; s[len]; len++) { if (s[len] == '\\' && s[len + 1]) len++; @@ -751,6 +755,14 @@ static int do_mount(const char *mnt, char **typep, mode_t rootmode, } else if (begins_with(s, subtype_str)) { if (!get_string_opt(s, len, subtype_str, &subtype)) goto err; + } else if (begins_with(s, rootmode_str)) { + check_rootmode = strtol(s + rootmode_len, &ref, 8); + if (errno == EINVAL || errno == ERANGE + || *ref != '\0') { + fprintf(stderr, + "Rootmode argument is invalid\n"); + goto err; + } } else if (opt_eq(s, len, "blkdev")) { if (getuid() != 0) { fprintf(stderr, @@ -810,6 +822,9 @@ static int do_mount(const char *mnt, char **typep, mode_t rootmode, if (res == -1) goto err; + if (check_rootmode) + rootmode = check_rootmode; + sprintf(d, "fd=%i,rootmode=%o,user_id=%i,group_id=%i", fd, rootmode, getuid(), getgid()); -- 1.8.3.2 |