diff options
Diffstat (limited to 'security/selinux/hooks.c')
-rw-r--r-- | security/selinux/hooks.c | 96 |
1 files changed, 48 insertions, 48 deletions
diff --git a/security/selinux/hooks.c b/security/selinux/hooks.c index 97b7e2738097..24e1b1885de7 100644 --- a/security/selinux/hooks.c +++ b/security/selinux/hooks.c | |||
@@ -22,7 +22,6 @@ | |||
22 | * as published by the Free Software Foundation. | 22 | * as published by the Free Software Foundation. |
23 | */ | 23 | */ |
24 | 24 | ||
25 | #include <linux/module.h> | ||
26 | #include <linux/init.h> | 25 | #include <linux/init.h> |
27 | #include <linux/kernel.h> | 26 | #include <linux/kernel.h> |
28 | #include <linux/ptrace.h> | 27 | #include <linux/ptrace.h> |
@@ -86,6 +85,7 @@ | |||
86 | extern unsigned int policydb_loaded_version; | 85 | extern unsigned int policydb_loaded_version; |
87 | extern int selinux_nlmsg_lookup(u16 sclass, u16 nlmsg_type, u32 *perm); | 86 | extern int selinux_nlmsg_lookup(u16 sclass, u16 nlmsg_type, u32 *perm); |
88 | extern int selinux_compat_net; | 87 | extern int selinux_compat_net; |
88 | extern struct security_operations *security_ops; | ||
89 | 89 | ||
90 | #ifdef CONFIG_SECURITY_SELINUX_DEVELOP | 90 | #ifdef CONFIG_SECURITY_SELINUX_DEVELOP |
91 | int selinux_enforcing = 0; | 91 | int selinux_enforcing = 0; |
@@ -2297,6 +2297,25 @@ static int selinux_inode_getattr(struct vfsmount *mnt, struct dentry *dentry) | |||
2297 | return dentry_has_perm(current, mnt, dentry, FILE__GETATTR); | 2297 | return dentry_has_perm(current, mnt, dentry, FILE__GETATTR); |
2298 | } | 2298 | } |
2299 | 2299 | ||
2300 | static int selinux_inode_setotherxattr(struct dentry *dentry, char *name) | ||
2301 | { | ||
2302 | if (!strncmp(name, XATTR_SECURITY_PREFIX, | ||
2303 | sizeof XATTR_SECURITY_PREFIX - 1)) { | ||
2304 | if (!strcmp(name, XATTR_NAME_CAPS)) { | ||
2305 | if (!capable(CAP_SETFCAP)) | ||
2306 | return -EPERM; | ||
2307 | } else if (!capable(CAP_SYS_ADMIN)) { | ||
2308 | /* A different attribute in the security namespace. | ||
2309 | Restrict to administrator. */ | ||
2310 | return -EPERM; | ||
2311 | } | ||
2312 | } | ||
2313 | |||
2314 | /* Not an attribute we recognize, so just check the | ||
2315 | ordinary setattr permission. */ | ||
2316 | return dentry_has_perm(current, NULL, dentry, FILE__SETATTR); | ||
2317 | } | ||
2318 | |||
2300 | static int selinux_inode_setxattr(struct dentry *dentry, char *name, void *value, size_t size, int flags) | 2319 | static int selinux_inode_setxattr(struct dentry *dentry, char *name, void *value, size_t size, int flags) |
2301 | { | 2320 | { |
2302 | struct task_security_struct *tsec = current->security; | 2321 | struct task_security_struct *tsec = current->security; |
@@ -2307,19 +2326,8 @@ static int selinux_inode_setxattr(struct dentry *dentry, char *name, void *value | |||
2307 | u32 newsid; | 2326 | u32 newsid; |
2308 | int rc = 0; | 2327 | int rc = 0; |
2309 | 2328 | ||
2310 | if (strcmp(name, XATTR_NAME_SELINUX)) { | 2329 | if (strcmp(name, XATTR_NAME_SELINUX)) |
2311 | if (!strncmp(name, XATTR_SECURITY_PREFIX, | 2330 | return selinux_inode_setotherxattr(dentry, name); |
2312 | sizeof XATTR_SECURITY_PREFIX - 1) && | ||
2313 | !capable(CAP_SYS_ADMIN)) { | ||
2314 | /* A different attribute in the security namespace. | ||
2315 | Restrict to administrator. */ | ||
2316 | return -EPERM; | ||
2317 | } | ||
2318 | |||
2319 | /* Not an attribute we recognize, so just check the | ||
2320 | ordinary setattr permission. */ | ||
2321 | return dentry_has_perm(current, NULL, dentry, FILE__SETATTR); | ||
2322 | } | ||
2323 | 2331 | ||
2324 | sbsec = inode->i_sb->s_security; | 2332 | sbsec = inode->i_sb->s_security; |
2325 | if (sbsec->behavior == SECURITY_FS_USE_MNTPOINT) | 2333 | if (sbsec->behavior == SECURITY_FS_USE_MNTPOINT) |
@@ -2393,31 +2401,14 @@ static int selinux_inode_listxattr (struct dentry *dentry) | |||
2393 | 2401 | ||
2394 | static int selinux_inode_removexattr (struct dentry *dentry, char *name) | 2402 | static int selinux_inode_removexattr (struct dentry *dentry, char *name) |
2395 | { | 2403 | { |
2396 | if (strcmp(name, XATTR_NAME_SELINUX)) { | 2404 | if (strcmp(name, XATTR_NAME_SELINUX)) |
2397 | if (!strncmp(name, XATTR_SECURITY_PREFIX, | 2405 | return selinux_inode_setotherxattr(dentry, name); |
2398 | sizeof XATTR_SECURITY_PREFIX - 1) && | ||
2399 | !capable(CAP_SYS_ADMIN)) { | ||
2400 | /* A different attribute in the security namespace. | ||
2401 | Restrict to administrator. */ | ||
2402 | return -EPERM; | ||
2403 | } | ||
2404 | |||
2405 | /* Not an attribute we recognize, so just check the | ||
2406 | ordinary setattr permission. Might want a separate | ||
2407 | permission for removexattr. */ | ||
2408 | return dentry_has_perm(current, NULL, dentry, FILE__SETATTR); | ||
2409 | } | ||
2410 | 2406 | ||
2411 | /* No one is allowed to remove a SELinux security label. | 2407 | /* No one is allowed to remove a SELinux security label. |
2412 | You can change the label, but all data must be labeled. */ | 2408 | You can change the label, but all data must be labeled. */ |
2413 | return -EACCES; | 2409 | return -EACCES; |
2414 | } | 2410 | } |
2415 | 2411 | ||
2416 | static const char *selinux_inode_xattr_getsuffix(void) | ||
2417 | { | ||
2418 | return XATTR_SELINUX_SUFFIX; | ||
2419 | } | ||
2420 | |||
2421 | /* | 2412 | /* |
2422 | * Copy the in-core inode security context value to the user. If the | 2413 | * Copy the in-core inode security context value to the user. If the |
2423 | * getxattr() prior to this succeeded, check to see if we need to | 2414 | * getxattr() prior to this succeeded, check to see if we need to |
@@ -2464,6 +2455,16 @@ static int selinux_inode_listsecurity(struct inode *inode, char *buffer, size_t | |||
2464 | return len; | 2455 | return len; |
2465 | } | 2456 | } |
2466 | 2457 | ||
2458 | static int selinux_inode_need_killpriv(struct dentry *dentry) | ||
2459 | { | ||
2460 | return secondary_ops->inode_need_killpriv(dentry); | ||
2461 | } | ||
2462 | |||
2463 | static int selinux_inode_killpriv(struct dentry *dentry) | ||
2464 | { | ||
2465 | return secondary_ops->inode_killpriv(dentry); | ||
2466 | } | ||
2467 | |||
2467 | /* file security operations */ | 2468 | /* file security operations */ |
2468 | 2469 | ||
2469 | static int selinux_revalidate_file_permission(struct file *file, int mask) | 2470 | static int selinux_revalidate_file_permission(struct file *file, int mask) |
@@ -2882,6 +2883,12 @@ static int selinux_task_setnice(struct task_struct *p, int nice) | |||
2882 | 2883 | ||
2883 | static int selinux_task_setioprio(struct task_struct *p, int ioprio) | 2884 | static int selinux_task_setioprio(struct task_struct *p, int ioprio) |
2884 | { | 2885 | { |
2886 | int rc; | ||
2887 | |||
2888 | rc = secondary_ops->task_setioprio(p, ioprio); | ||
2889 | if (rc) | ||
2890 | return rc; | ||
2891 | |||
2885 | return task_has_perm(current, p, PROCESS__SETSCHED); | 2892 | return task_has_perm(current, p, PROCESS__SETSCHED); |
2886 | } | 2893 | } |
2887 | 2894 | ||
@@ -2911,6 +2918,12 @@ static int selinux_task_setrlimit(unsigned int resource, struct rlimit *new_rlim | |||
2911 | 2918 | ||
2912 | static int selinux_task_setscheduler(struct task_struct *p, int policy, struct sched_param *lp) | 2919 | static int selinux_task_setscheduler(struct task_struct *p, int policy, struct sched_param *lp) |
2913 | { | 2920 | { |
2921 | int rc; | ||
2922 | |||
2923 | rc = secondary_ops->task_setscheduler(p, policy, lp); | ||
2924 | if (rc) | ||
2925 | return rc; | ||
2926 | |||
2914 | return task_has_perm(current, p, PROCESS__SETSCHED); | 2927 | return task_has_perm(current, p, PROCESS__SETSCHED); |
2915 | } | 2928 | } |
2916 | 2929 | ||
@@ -4536,19 +4549,6 @@ static int selinux_register_security (const char *name, struct security_operatio | |||
4536 | return 0; | 4549 | return 0; |
4537 | } | 4550 | } |
4538 | 4551 | ||
4539 | static int selinux_unregister_security (const char *name, struct security_operations *ops) | ||
4540 | { | ||
4541 | if (ops != secondary_ops) { | ||
4542 | printk(KERN_ERR "%s: trying to unregister a security module " | ||
4543 | "that is not registered.\n", __FUNCTION__); | ||
4544 | return -EINVAL; | ||
4545 | } | ||
4546 | |||
4547 | secondary_ops = original_ops; | ||
4548 | |||
4549 | return 0; | ||
4550 | } | ||
4551 | |||
4552 | static void selinux_d_instantiate (struct dentry *dentry, struct inode *inode) | 4552 | static void selinux_d_instantiate (struct dentry *dentry, struct inode *inode) |
4553 | { | 4553 | { |
4554 | if (inode) | 4554 | if (inode) |
@@ -4826,10 +4826,11 @@ static struct security_operations selinux_ops = { | |||
4826 | .inode_getxattr = selinux_inode_getxattr, | 4826 | .inode_getxattr = selinux_inode_getxattr, |
4827 | .inode_listxattr = selinux_inode_listxattr, | 4827 | .inode_listxattr = selinux_inode_listxattr, |
4828 | .inode_removexattr = selinux_inode_removexattr, | 4828 | .inode_removexattr = selinux_inode_removexattr, |
4829 | .inode_xattr_getsuffix = selinux_inode_xattr_getsuffix, | ||
4830 | .inode_getsecurity = selinux_inode_getsecurity, | 4829 | .inode_getsecurity = selinux_inode_getsecurity, |
4831 | .inode_setsecurity = selinux_inode_setsecurity, | 4830 | .inode_setsecurity = selinux_inode_setsecurity, |
4832 | .inode_listsecurity = selinux_inode_listsecurity, | 4831 | .inode_listsecurity = selinux_inode_listsecurity, |
4832 | .inode_need_killpriv = selinux_inode_need_killpriv, | ||
4833 | .inode_killpriv = selinux_inode_killpriv, | ||
4833 | 4834 | ||
4834 | .file_permission = selinux_file_permission, | 4835 | .file_permission = selinux_file_permission, |
4835 | .file_alloc_security = selinux_file_alloc_security, | 4836 | .file_alloc_security = selinux_file_alloc_security, |
@@ -4894,7 +4895,6 @@ static struct security_operations selinux_ops = { | |||
4894 | .sem_semop = selinux_sem_semop, | 4895 | .sem_semop = selinux_sem_semop, |
4895 | 4896 | ||
4896 | .register_security = selinux_register_security, | 4897 | .register_security = selinux_register_security, |
4897 | .unregister_security = selinux_unregister_security, | ||
4898 | 4898 | ||
4899 | .d_instantiate = selinux_d_instantiate, | 4899 | .d_instantiate = selinux_d_instantiate, |
4900 | 4900 | ||