diff options
Diffstat (limited to 'security/selinux/hooks.c')
| -rw-r--r-- | security/selinux/hooks.c | 22 |
1 files changed, 13 insertions, 9 deletions
diff --git a/security/selinux/hooks.c b/security/selinux/hooks.c index dbeaa783b2a9..00815973d412 100644 --- a/security/selinux/hooks.c +++ b/security/selinux/hooks.c | |||
| @@ -1433,12 +1433,13 @@ static int current_has_perm(const struct task_struct *tsk, | |||
| 1433 | 1433 | ||
| 1434 | /* Check whether a task is allowed to use a capability. */ | 1434 | /* Check whether a task is allowed to use a capability. */ |
| 1435 | static int task_has_capability(struct task_struct *tsk, | 1435 | static int task_has_capability(struct task_struct *tsk, |
| 1436 | const struct cred *cred, | ||
| 1436 | int cap, int audit) | 1437 | int cap, int audit) |
| 1437 | { | 1438 | { |
| 1438 | struct avc_audit_data ad; | 1439 | struct avc_audit_data ad; |
| 1439 | struct av_decision avd; | 1440 | struct av_decision avd; |
| 1440 | u16 sclass; | 1441 | u16 sclass; |
| 1441 | u32 sid = task_sid(tsk); | 1442 | u32 sid = cred_sid(cred); |
| 1442 | u32 av = CAP_TO_MASK(cap); | 1443 | u32 av = CAP_TO_MASK(cap); |
| 1443 | int rc; | 1444 | int rc; |
| 1444 | 1445 | ||
| @@ -1865,15 +1866,16 @@ static int selinux_capset(struct cred *new, const struct cred *old, | |||
| 1865 | return cred_has_perm(old, new, PROCESS__SETCAP); | 1866 | return cred_has_perm(old, new, PROCESS__SETCAP); |
| 1866 | } | 1867 | } |
| 1867 | 1868 | ||
| 1868 | static int selinux_capable(struct task_struct *tsk, int cap, int audit) | 1869 | static int selinux_capable(struct task_struct *tsk, const struct cred *cred, |
| 1870 | int cap, int audit) | ||
| 1869 | { | 1871 | { |
| 1870 | int rc; | 1872 | int rc; |
| 1871 | 1873 | ||
| 1872 | rc = secondary_ops->capable(tsk, cap, audit); | 1874 | rc = secondary_ops->capable(tsk, cred, cap, audit); |
| 1873 | if (rc) | 1875 | if (rc) |
| 1874 | return rc; | 1876 | return rc; |
| 1875 | 1877 | ||
| 1876 | return task_has_capability(tsk, cap, audit); | 1878 | return task_has_capability(tsk, cred, cap, audit); |
| 1877 | } | 1879 | } |
| 1878 | 1880 | ||
| 1879 | static int selinux_sysctl_get_sid(ctl_table *table, u16 tclass, u32 *sid) | 1881 | static int selinux_sysctl_get_sid(ctl_table *table, u16 tclass, u32 *sid) |
| @@ -2037,7 +2039,8 @@ static int selinux_vm_enough_memory(struct mm_struct *mm, long pages) | |||
| 2037 | { | 2039 | { |
| 2038 | int rc, cap_sys_admin = 0; | 2040 | int rc, cap_sys_admin = 0; |
| 2039 | 2041 | ||
| 2040 | rc = selinux_capable(current, CAP_SYS_ADMIN, SECURITY_CAP_NOAUDIT); | 2042 | rc = selinux_capable(current, current_cred(), CAP_SYS_ADMIN, |
| 2043 | SECURITY_CAP_NOAUDIT); | ||
| 2041 | if (rc == 0) | 2044 | if (rc == 0) |
| 2042 | cap_sys_admin = 1; | 2045 | cap_sys_admin = 1; |
| 2043 | 2046 | ||
| @@ -2880,7 +2883,8 @@ static int selinux_inode_getsecurity(const struct inode *inode, const char *name | |||
| 2880 | * and lack of permission just means that we fall back to the | 2883 | * and lack of permission just means that we fall back to the |
| 2881 | * in-core context value, not a denial. | 2884 | * in-core context value, not a denial. |
| 2882 | */ | 2885 | */ |
| 2883 | error = selinux_capable(current, CAP_MAC_ADMIN, SECURITY_CAP_NOAUDIT); | 2886 | error = selinux_capable(current, current_cred(), CAP_MAC_ADMIN, |
| 2887 | SECURITY_CAP_NOAUDIT); | ||
| 2884 | if (!error) | 2888 | if (!error) |
| 2885 | error = security_sid_to_context_force(isec->sid, &context, | 2889 | error = security_sid_to_context_force(isec->sid, &context, |
| 2886 | &size); | 2890 | &size); |
| @@ -4185,7 +4189,7 @@ static int selinux_sock_rcv_skb_iptables_compat(struct sock *sk, | |||
| 4185 | static int selinux_sock_rcv_skb_compat(struct sock *sk, struct sk_buff *skb, | 4189 | static int selinux_sock_rcv_skb_compat(struct sock *sk, struct sk_buff *skb, |
| 4186 | u16 family) | 4190 | u16 family) |
| 4187 | { | 4191 | { |
| 4188 | int err; | 4192 | int err = 0; |
| 4189 | struct sk_security_struct *sksec = sk->sk_security; | 4193 | struct sk_security_struct *sksec = sk->sk_security; |
| 4190 | u32 peer_sid; | 4194 | u32 peer_sid; |
| 4191 | u32 sk_sid = sksec->sid; | 4195 | u32 sk_sid = sksec->sid; |
| @@ -4202,7 +4206,7 @@ static int selinux_sock_rcv_skb_compat(struct sock *sk, struct sk_buff *skb, | |||
| 4202 | if (selinux_compat_net) | 4206 | if (selinux_compat_net) |
| 4203 | err = selinux_sock_rcv_skb_iptables_compat(sk, skb, &ad, | 4207 | err = selinux_sock_rcv_skb_iptables_compat(sk, skb, &ad, |
| 4204 | family, addrp); | 4208 | family, addrp); |
| 4205 | else | 4209 | else if (selinux_secmark_enabled()) |
| 4206 | err = avc_has_perm(sk_sid, skb->secmark, SECCLASS_PACKET, | 4210 | err = avc_has_perm(sk_sid, skb->secmark, SECCLASS_PACKET, |
| 4207 | PACKET__RECV, &ad); | 4211 | PACKET__RECV, &ad); |
| 4208 | if (err) | 4212 | if (err) |
| @@ -4705,7 +4709,7 @@ static unsigned int selinux_ip_postroute_compat(struct sk_buff *skb, | |||
| 4705 | if (selinux_ip_postroute_iptables_compat(skb->sk, ifindex, | 4709 | if (selinux_ip_postroute_iptables_compat(skb->sk, ifindex, |
| 4706 | &ad, family, addrp)) | 4710 | &ad, family, addrp)) |
| 4707 | return NF_DROP; | 4711 | return NF_DROP; |
| 4708 | } else { | 4712 | } else if (selinux_secmark_enabled()) { |
| 4709 | if (avc_has_perm(sksec->sid, skb->secmark, | 4713 | if (avc_has_perm(sksec->sid, skb->secmark, |
| 4710 | SECCLASS_PACKET, PACKET__SEND, &ad)) | 4714 | SECCLASS_PACKET, PACKET__SEND, &ad)) |
| 4711 | return NF_DROP; | 4715 | return NF_DROP; |
