new helper: security_sb_eat_lsm_opts()
combination of alloc_secdata(), security_sb_copy_data(), security_sb_parse_opt_str() and free_secdata(). Reviewed-by: David Howells <dhowells@redhat.com> Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
This commit is contained in:
Родитель
c039bc3c24
Коммит
f5c0c26d90
|
@ -1461,20 +1461,7 @@ out:
|
||||||
static int parse_security_options(char *orig_opts,
|
static int parse_security_options(char *orig_opts,
|
||||||
struct security_mnt_opts *sec_opts)
|
struct security_mnt_opts *sec_opts)
|
||||||
{
|
{
|
||||||
char *secdata = NULL;
|
return security_sb_eat_lsm_opts(orig_opts, sec_opts);
|
||||||
int ret = 0;
|
|
||||||
|
|
||||||
secdata = alloc_secdata();
|
|
||||||
if (!secdata)
|
|
||||||
return -ENOMEM;
|
|
||||||
ret = security_sb_copy_data(orig_opts, secdata);
|
|
||||||
if (ret) {
|
|
||||||
free_secdata(secdata);
|
|
||||||
return ret;
|
|
||||||
}
|
|
||||||
ret = security_sb_parse_opts_str(secdata, sec_opts);
|
|
||||||
free_secdata(secdata);
|
|
||||||
return ret;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static int setup_security_options(struct btrfs_fs_info *fs_info,
|
static int setup_security_options(struct btrfs_fs_info *fs_info,
|
||||||
|
|
|
@ -2312,16 +2312,7 @@ static int do_remount(struct path *path, int ms_flags, int sb_flags,
|
||||||
|
|
||||||
security_init_mnt_opts(&opts);
|
security_init_mnt_opts(&opts);
|
||||||
if (data && !(sb->s_type->fs_flags & FS_BINARY_MOUNTDATA)) {
|
if (data && !(sb->s_type->fs_flags & FS_BINARY_MOUNTDATA)) {
|
||||||
char *secdata = alloc_secdata();
|
err = security_sb_eat_lsm_opts(data, &opts);
|
||||||
if (!secdata)
|
|
||||||
return -ENOMEM;
|
|
||||||
err = security_sb_copy_data(data, secdata);
|
|
||||||
if (err) {
|
|
||||||
free_secdata(secdata);
|
|
||||||
return err;
|
|
||||||
}
|
|
||||||
err = security_sb_parse_opts_str(secdata, &opts);
|
|
||||||
free_secdata(secdata);
|
|
||||||
if (err)
|
if (err)
|
||||||
return err;
|
return err;
|
||||||
}
|
}
|
||||||
|
|
|
@ -1206,7 +1206,7 @@ static int nfs_get_option_ul_bound(substring_t args[], unsigned long *option,
|
||||||
static int nfs_parse_mount_options(char *raw,
|
static int nfs_parse_mount_options(char *raw,
|
||||||
struct nfs_parsed_mount_data *mnt)
|
struct nfs_parsed_mount_data *mnt)
|
||||||
{
|
{
|
||||||
char *p, *string, *secdata;
|
char *p, *string;
|
||||||
int rc, sloppy = 0, invalid_option = 0;
|
int rc, sloppy = 0, invalid_option = 0;
|
||||||
unsigned short protofamily = AF_UNSPEC;
|
unsigned short protofamily = AF_UNSPEC;
|
||||||
unsigned short mountfamily = AF_UNSPEC;
|
unsigned short mountfamily = AF_UNSPEC;
|
||||||
|
@ -1217,20 +1217,10 @@ static int nfs_parse_mount_options(char *raw,
|
||||||
}
|
}
|
||||||
dfprintk(MOUNT, "NFS: nfs mount opts='%s'\n", raw);
|
dfprintk(MOUNT, "NFS: nfs mount opts='%s'\n", raw);
|
||||||
|
|
||||||
secdata = alloc_secdata();
|
rc = security_sb_eat_lsm_opts(raw, &mnt->lsm_opts);
|
||||||
if (!secdata)
|
|
||||||
goto out_nomem;
|
|
||||||
|
|
||||||
rc = security_sb_copy_data(raw, secdata);
|
|
||||||
if (rc)
|
if (rc)
|
||||||
goto out_security_failure;
|
goto out_security_failure;
|
||||||
|
|
||||||
rc = security_sb_parse_opts_str(secdata, &mnt->lsm_opts);
|
|
||||||
if (rc)
|
|
||||||
goto out_security_failure;
|
|
||||||
|
|
||||||
free_secdata(secdata);
|
|
||||||
|
|
||||||
while ((p = strsep(&raw, ",")) != NULL) {
|
while ((p = strsep(&raw, ",")) != NULL) {
|
||||||
substring_t args[MAX_OPT_ARGS];
|
substring_t args[MAX_OPT_ARGS];
|
||||||
unsigned long option;
|
unsigned long option;
|
||||||
|
@ -1682,7 +1672,6 @@ out_nomem:
|
||||||
printk(KERN_INFO "NFS: not enough memory to parse option\n");
|
printk(KERN_INFO "NFS: not enough memory to parse option\n");
|
||||||
return 0;
|
return 0;
|
||||||
out_security_failure:
|
out_security_failure:
|
||||||
free_secdata(secdata);
|
|
||||||
printk(KERN_INFO "NFS: security options invalid: %d\n", rc);
|
printk(KERN_INFO "NFS: security options invalid: %d\n", rc);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
13
fs/super.c
13
fs/super.c
|
@ -1252,18 +1252,7 @@ mount_fs(struct file_system_type *type, int flags, const char *name, void *data)
|
||||||
security_init_mnt_opts(&opts);
|
security_init_mnt_opts(&opts);
|
||||||
|
|
||||||
if (data && !(type->fs_flags & FS_BINARY_MOUNTDATA)) {
|
if (data && !(type->fs_flags & FS_BINARY_MOUNTDATA)) {
|
||||||
char *secdata = alloc_secdata();
|
error = security_sb_eat_lsm_opts(data, &opts);
|
||||||
if (!secdata)
|
|
||||||
return ERR_PTR(-ENOMEM);
|
|
||||||
|
|
||||||
error = security_sb_copy_data(data, secdata);
|
|
||||||
if (error) {
|
|
||||||
free_secdata(secdata);
|
|
||||||
return ERR_PTR(error);
|
|
||||||
}
|
|
||||||
|
|
||||||
error = security_sb_parse_opts_str(secdata, &opts);
|
|
||||||
free_secdata(secdata);
|
|
||||||
if (error)
|
if (error)
|
||||||
return ERR_PTR(error);
|
return ERR_PTR(error);
|
||||||
}
|
}
|
||||||
|
|
|
@ -248,7 +248,7 @@ void security_bprm_committing_creds(struct linux_binprm *bprm);
|
||||||
void security_bprm_committed_creds(struct linux_binprm *bprm);
|
void security_bprm_committed_creds(struct linux_binprm *bprm);
|
||||||
int security_sb_alloc(struct super_block *sb);
|
int security_sb_alloc(struct super_block *sb);
|
||||||
void security_sb_free(struct super_block *sb);
|
void security_sb_free(struct super_block *sb);
|
||||||
int security_sb_copy_data(char *orig, char *copy);
|
int security_sb_eat_lsm_opts(char *options, struct security_mnt_opts *opts);
|
||||||
int security_sb_remount(struct super_block *sb, struct security_mnt_opts *opts);
|
int security_sb_remount(struct super_block *sb, struct security_mnt_opts *opts);
|
||||||
int security_sb_kern_mount(struct super_block *sb, int flags,
|
int security_sb_kern_mount(struct super_block *sb, int flags,
|
||||||
struct security_mnt_opts *opts);
|
struct security_mnt_opts *opts);
|
||||||
|
@ -556,7 +556,8 @@ static inline int security_sb_alloc(struct super_block *sb)
|
||||||
static inline void security_sb_free(struct super_block *sb)
|
static inline void security_sb_free(struct super_block *sb)
|
||||||
{ }
|
{ }
|
||||||
|
|
||||||
static inline int security_sb_copy_data(char *orig, char *copy)
|
static inline int security_sb_eat_lsm_opts(char *options,
|
||||||
|
struct security_mnt_opts *opts)
|
||||||
{
|
{
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -1823,28 +1824,5 @@ static inline void security_bpf_prog_free(struct bpf_prog_aux *aux)
|
||||||
#endif /* CONFIG_SECURITY */
|
#endif /* CONFIG_SECURITY */
|
||||||
#endif /* CONFIG_BPF_SYSCALL */
|
#endif /* CONFIG_BPF_SYSCALL */
|
||||||
|
|
||||||
#ifdef CONFIG_SECURITY
|
|
||||||
|
|
||||||
static inline char *alloc_secdata(void)
|
|
||||||
{
|
|
||||||
return (char *)get_zeroed_page(GFP_KERNEL);
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void free_secdata(void *secdata)
|
|
||||||
{
|
|
||||||
free_page((unsigned long)secdata);
|
|
||||||
}
|
|
||||||
|
|
||||||
#else
|
|
||||||
|
|
||||||
static inline char *alloc_secdata(void)
|
|
||||||
{
|
|
||||||
return (char *)1;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void free_secdata(void *secdata)
|
|
||||||
{ }
|
|
||||||
#endif /* CONFIG_SECURITY */
|
|
||||||
|
|
||||||
#endif /* ! __LINUX_SECURITY_H */
|
#endif /* ! __LINUX_SECURITY_H */
|
||||||
|
|
||||||
|
|
|
@ -384,11 +384,20 @@ void security_sb_free(struct super_block *sb)
|
||||||
call_void_hook(sb_free_security, sb);
|
call_void_hook(sb_free_security, sb);
|
||||||
}
|
}
|
||||||
|
|
||||||
int security_sb_copy_data(char *orig, char *copy)
|
int security_sb_eat_lsm_opts(char *options, struct security_mnt_opts *opts)
|
||||||
{
|
{
|
||||||
return call_int_hook(sb_copy_data, 0, orig, copy);
|
char *s = (char *)get_zeroed_page(GFP_KERNEL);
|
||||||
|
int err;
|
||||||
|
|
||||||
|
if (!s)
|
||||||
|
return -ENOMEM;
|
||||||
|
err = call_int_hook(sb_copy_data, 0, options, s);
|
||||||
|
if (!err)
|
||||||
|
err = call_int_hook(sb_parse_opts_str, 0, s, opts);
|
||||||
|
free_page((unsigned long)s);
|
||||||
|
return err;
|
||||||
}
|
}
|
||||||
EXPORT_SYMBOL(security_sb_copy_data);
|
EXPORT_SYMBOL(security_sb_eat_lsm_opts);
|
||||||
|
|
||||||
int security_sb_remount(struct super_block *sb,
|
int security_sb_remount(struct super_block *sb,
|
||||||
struct security_mnt_opts *opts)
|
struct security_mnt_opts *opts)
|
||||||
|
|
Загрузка…
Ссылка в новой задаче