From: Jeff Mahoney <jeffm@suse.com>
To: Ian Kent <raven@themaw.net>, autofs@vger.kernel.org
Subject: Re: [PATCH] autofs: improve scalability of direct mount path component creation
Date: Tue, 22 Mar 2016 10:38:37 -0400 [thread overview]
Message-ID: <56F158ED.5070001@suse.com> (raw)
In-Reply-To: <56F152FA.1000205@suse.com>
[-- Attachment #1.1: Type: text/plain, Size: 5930 bytes --]
On 3/22/16 10:13 AM, Jeff Mahoney wrote:
> With direct mounts, we want to avoid creating path components on
> remote file systems unless that file system is the root file system.
>
> The check boils down to allowing the mkdir if:
> 1/ If it's the root directory, or
> 2/ If it's not a remote file system, or
> 3/ If it's a remote file system that's the root file system
>
> We can do that without parsing the mount table and can
> improve startup time for all cases.
I did test this in the expected scenarios:
- With an NFS (ch)root, direct mount on NFS root, created.
- With an NFS (ch)root, direct mount on NFS mount, did not create.
- With a local root, direct mount on root fs, created.
- With a local root, direct mount on another local fs, created.
- With a local root, direct mount on NFS, did not create.
-Jeff
> Signed-off-by: Jeff Mahoney <jeffm@suse.com>
> ---
> daemon/automount.c | 56 +++++++++++++++++++++++++++++++++++++++--------------
> include/automount.h | 2 ++
> include/mounts.h | 1 -
> lib/mounts.c | 45 ------------------------------------------
> 4 files changed, 44 insertions(+), 60 deletions(-)
>
> diff --git a/daemon/automount.c b/daemon/automount.c
> index 74e62a1..9d07425 100644
> --- a/daemon/automount.c
> +++ b/daemon/automount.c
> @@ -98,10 +98,25 @@ static int umount_all(struct autofs_point *ap, int force);
>
> extern struct master *master_list;
>
> +static int is_remote_fstype(unsigned int fs_type)
> +{
> + int ret = 0;
> + switch (fs_type) {
> + case SMB_SUPER_MAGIC:
> + case CIFS_MAGIC_NUMBER:
> + case NCP_SUPER_MAGIC:
> + case NFS_SUPER_MAGIC:
> + ret = 1;
> + break;
> + };
> + return ret;
> +}
> +
> static int do_mkdir(const char *parent, const char *path, mode_t mode)
> {
> int status;
> - struct stat st;
> + mode_t mask;
> + struct stat st, root;
> struct statfs fs;
>
> /* If path exists we're done */
> @@ -114,24 +129,37 @@ static int do_mkdir(const char *parent, const char *path, mode_t mode)
> }
>
> /*
> - * If we're trying to create a directory within an autofs fs
> - * or the path is contained in a localy mounted fs go ahead.
> + * We don't want to create the path on a remote file system
> + * unless it's the root file system.
> + * An empty parent means it's the root directory and always ok.
> */
> - status = -1;
> - if (*parent)
> + if (*parent) {
> status = statfs(parent, &fs);
> - if ((status != -1 && fs.f_type == (__SWORD_TYPE) AUTOFS_SUPER_MAGIC) ||
> - contained_in_local_fs(path)) {
> - mode_t mask = umask(0022);
> - int ret = mkdir(path, mode);
> - (void) umask(mask);
> - if (ret == -1) {
> - errno = EACCES;
> - return 0;
> + if (status == -1)
> + goto fail;
> +
> + if (is_remote_fstype(fs.f_type)) {
> + status = stat(parent, &st);
> + if (status == -1)
> + goto fail;
> +
> + status = stat("/", &root);
> + if (status == -1)
> + goto fail;
> +
> + if (st.st_dev != root.st_dev)
> + goto fail;
> }
> - return 1;
> }
>
> + mask = umask(0022);
> + status = mkdir(path, mode);
> + (void) umask(mask);
> + if (status == -1)
> + goto fail;
> +
> + return 1;
> +fail:
> errno = EACCES;
> return 0;
> }
> diff --git a/include/automount.h b/include/automount.h
> index 2cf0611..c0f5fbf 100644
> --- a/include/automount.h
> +++ b/include/automount.h
> @@ -75,6 +75,8 @@ int load_autofs4_module(void);
> #define AUTOFS_SUPER_MAGIC 0x00000187L
> #define SMB_SUPER_MAGIC 0x0000517BL
> #define CIFS_MAGIC_NUMBER 0xFF534D42L
> +#define NCP_SUPER_MAGIC 0x0000564CL
> +#define NFS_SUPER_MAGIC 0x00006969L
>
> /* This sould be enough for at least 20 host aliases */
> #define HOST_ENT_BUF_SIZE 2048
> diff --git a/include/mounts.h b/include/mounts.h
> index cce646a..489025c 100644
> --- a/include/mounts.h
> +++ b/include/mounts.h
> @@ -101,7 +101,6 @@ int ext_mount_remove(struct list_head *, const char *);
> struct mnt_list *get_mnt_list(const char *table, const char *path, int include);
> struct mnt_list *reverse_mnt_list(struct mnt_list *list);
> void free_mnt_list(struct mnt_list *list);
> -int contained_in_local_fs(const char *path);
> int is_mounted(const char *table, const char *path, unsigned int type);
> int has_fstab_option(const char *opt);
> void tree_free_mnt_tree(struct mnt_list *tree);
> diff --git a/lib/mounts.c b/lib/mounts.c
> index 455bdca..1d1b4da 100644
> --- a/lib/mounts.c
> +++ b/lib/mounts.c
> @@ -941,51 +941,6 @@ void free_mnt_list(struct mnt_list *list)
> }
> }
>
> -int contained_in_local_fs(const char *path)
> -{
> - struct mnt_list *mnts, *this;
> - size_t pathlen = strlen(path);
> - int ret;
> -
> - if (!path || !pathlen || pathlen > PATH_MAX)
> - return 0;
> -
> - mnts = get_mnt_list(_PATH_MOUNTED, "/", 1);
> - if (!mnts)
> - return 0;
> -
> - ret = 0;
> -
> - for (this = mnts; this != NULL; this = this->next) {
> - size_t len = strlen(this->path);
> -
> - if (!strncmp(path, this->path, len)) {
> - if (len > 1 && pathlen > len && path[len] != '/')
> - continue;
> - else if (len == 1 && this->path[0] == '/') {
> - /*
> - * always return true on rootfs, we don't
> - * want to break diskless clients.
> - */
> - ret = 1;
> - } else if (this->fs_name[0] == '/') {
> - if (strlen(this->fs_name) > 1) {
> - if (this->fs_name[1] != '/')
> - ret = 1;
> - } else
> - ret = 1;
> - } else if (!strncmp("LABEL=", this->fs_name, 6) ||
> - !strncmp("UUID=", this->fs_name, 5))
> - ret = 1;
> - break;
> - }
> - }
> -
> - free_mnt_list(mnts);
> -
> - return ret;
> -}
> -
> static int table_is_mounted(const char *table, const char *path, unsigned int type)
> {
> struct mntent *mnt;
>
--
Jeff Mahoney
SUSE Labs
[-- Attachment #2: OpenPGP digital signature --]
[-- Type: application/pgp-signature, Size: 881 bytes --]
next prev parent reply other threads:[~2016-03-22 14:38 UTC|newest]
Thread overview: 12+ messages / expand[flat|nested] mbox.gz Atom feed top
2016-03-18 20:44 [BUG] contained_in_local_fs will *always* return true Jeff Mahoney
2016-03-18 21:25 ` [PATCH] autofs: fix contained_in_local_fs and improve scalability Jeff Mahoney
2016-03-19 20:58 ` Jeff Mahoney
2016-03-21 3:44 ` Ian Kent
2016-03-21 22:08 ` Jeff Mahoney
2016-03-22 0:24 ` Ian Kent
2016-03-22 3:50 ` Jeff Mahoney
2016-03-22 14:13 ` [PATCH] autofs: improve scalability of direct mount path component creation Jeff Mahoney
2016-03-22 14:38 ` Jeff Mahoney [this message]
2016-03-24 1:23 ` Ian Kent
2016-03-22 1:24 ` [PATCH] autofs: fix contained_in_local_fs and improve scalability Marion, Mike
2016-03-20 13:05 ` [BUG] contained_in_local_fs will *always* return true Ian Kent
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=56F158ED.5070001@suse.com \
--to=jeffm@suse.com \
--cc=autofs@vger.kernel.org \
--cc=raven@themaw.net \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.