aboutsummaryrefslogtreecommitdiffstats
path: root/security/selinux/hooks.c
diff options
context:
space:
mode:
authorAl Viro <viro@zeniv.linux.org.uk>2018-12-01 23:06:57 -0500
committerAl Viro <viro@zeniv.linux.org.uk>2018-12-21 11:45:41 -0500
commitc039bc3c2498724946304a8f964244a9b6af1043 (patch)
treece98ee8e698a28cbaed969460457941e8b34f2e3 /security/selinux/hooks.c
parent6be8750b4cba8c37170f46b29841d112f1be749b (diff)
LSM: lift extracting and parsing LSM options into the caller of ->sb_remount()
This paves the way for retaining the LSM options from a common filesystem mount context during a mount parameter parsing phase to be instituted prior to actual mount/reconfiguration actions. Reviewed-by: David Howells <dhowells@redhat.com> Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
Diffstat (limited to 'security/selinux/hooks.c')
-rw-r--r--security/selinux/hooks.c47
1 files changed, 12 insertions, 35 deletions
diff --git a/security/selinux/hooks.c b/security/selinux/hooks.c
index ba229d4a64d3..ba3e2917bd24 100644
--- a/security/selinux/hooks.c
+++ b/security/selinux/hooks.c
@@ -2812,39 +2812,22 @@ out:
2812 return rc; 2812 return rc;
2813} 2813}
2814 2814
2815static int selinux_sb_remount(struct super_block *sb, void *data) 2815static int selinux_sb_remount(struct super_block *sb,
2816 struct security_mnt_opts *opts)
2816{ 2817{
2817 int rc, i, *flags; 2818 int i, *flags;
2818 struct security_mnt_opts opts; 2819 char **mount_options;
2819 char *secdata, **mount_options;
2820 struct superblock_security_struct *sbsec = sb->s_security; 2820 struct superblock_security_struct *sbsec = sb->s_security;
2821 2821
2822 if (!(sbsec->flags & SE_SBINITIALIZED)) 2822 if (!(sbsec->flags & SE_SBINITIALIZED))
2823 return 0; 2823 return 0;
2824 2824
2825 if (!data) 2825 mount_options = opts->mnt_opts;
2826 return 0; 2826 flags = opts->mnt_opts_flags;
2827
2828 if (sb->s_type->fs_flags & FS_BINARY_MOUNTDATA)
2829 return 0;
2830
2831 security_init_mnt_opts(&opts);
2832 secdata = alloc_secdata();
2833 if (!secdata)
2834 return -ENOMEM;
2835 rc = selinux_sb_copy_data(data, secdata);
2836 if (rc)
2837 goto out_free_secdata;
2838
2839 rc = selinux_parse_opts_str(secdata, &opts);
2840 if (rc)
2841 goto out_free_secdata;
2842 2827
2843 mount_options = opts.mnt_opts; 2828 for (i = 0; i < opts->num_mnt_opts; i++) {
2844 flags = opts.mnt_opts_flags;
2845
2846 for (i = 0; i < opts.num_mnt_opts; i++) {
2847 u32 sid; 2829 u32 sid;
2830 int rc;
2848 2831
2849 if (flags[i] == SBLABEL_MNT) 2832 if (flags[i] == SBLABEL_MNT)
2850 continue; 2833 continue;
@@ -2855,9 +2838,8 @@ static int selinux_sb_remount(struct super_block *sb, void *data)
2855 pr_warn("SELinux: security_context_str_to_sid" 2838 pr_warn("SELinux: security_context_str_to_sid"
2856 "(%s) failed for (dev %s, type %s) errno=%d\n", 2839 "(%s) failed for (dev %s, type %s) errno=%d\n",
2857 mount_options[i], sb->s_id, sb->s_type->name, rc); 2840 mount_options[i], sb->s_id, sb->s_type->name, rc);
2858 goto out_free_opts; 2841 return rc;
2859 } 2842 }
2860 rc = -EINVAL;
2861 switch (flags[i]) { 2843 switch (flags[i]) {
2862 case FSCONTEXT_MNT: 2844 case FSCONTEXT_MNT:
2863 if (bad_option(sbsec, FSCONTEXT_MNT, sbsec->sid, sid)) 2845 if (bad_option(sbsec, FSCONTEXT_MNT, sbsec->sid, sid))
@@ -2880,21 +2862,16 @@ static int selinux_sb_remount(struct super_block *sb, void *data)
2880 goto out_bad_option; 2862 goto out_bad_option;
2881 break; 2863 break;
2882 default: 2864 default:
2883 goto out_free_opts; 2865 return -EINVAL;
2884 } 2866 }
2885 } 2867 }
2868 return 0;
2886 2869
2887 rc = 0;
2888out_free_opts:
2889 security_free_mnt_opts(&opts);
2890out_free_secdata:
2891 free_secdata(secdata);
2892 return rc;
2893out_bad_option: 2870out_bad_option:
2894 pr_warn("SELinux: unable to change security options " 2871 pr_warn("SELinux: unable to change security options "
2895 "during remount (dev %s, type=%s)\n", sb->s_id, 2872 "during remount (dev %s, type=%s)\n", sb->s_id,
2896 sb->s_type->name); 2873 sb->s_type->name);
2897 goto out_free_opts; 2874 return -EINVAL;
2898} 2875}
2899 2876
2900static int selinux_sb_kern_mount(struct super_block *sb, int flags, 2877static int selinux_sb_kern_mount(struct super_block *sb, int flags,