diff options
Diffstat (limited to 'net')
-rw-r--r-- | net/core/sock.c | 11 | ||||
-rw-r--r-- | net/unix/af_unix.c | 27 |
2 files changed, 38 insertions, 0 deletions
diff --git a/net/core/sock.c b/net/core/sock.c index 5d820c37665..204a8dec65c 100644 --- a/net/core/sock.c +++ b/net/core/sock.c @@ -565,6 +565,13 @@ set_rcvbuf: ret = -ENONET; break; + case SO_PASSSEC: + if (valbool) + set_bit(SOCK_PASSSEC, &sock->flags); + else + clear_bit(SOCK_PASSSEC, &sock->flags); + break; + /* We implement the SO_SNDLOWAT etc to not be settable (1003.1g 5.3) */ default: @@ -723,6 +730,10 @@ int sock_getsockopt(struct socket *sock, int level, int optname, v.val = sk->sk_state == TCP_LISTEN; break; + case SO_PASSSEC: + v.val = test_bit(SOCK_PASSSEC, &sock->flags) ? 1 : 0; + break; + case SO_PEERSEC: return security_socket_getpeersec_stream(sock, optval, optlen, len); diff --git a/net/unix/af_unix.c b/net/unix/af_unix.c index d901465ce01..fd11d4048b5 100644 --- a/net/unix/af_unix.c +++ b/net/unix/af_unix.c @@ -128,6 +128,30 @@ static atomic_t unix_nr_socks = ATOMIC_INIT(0); #define UNIX_ABSTRACT(sk) (unix_sk(sk)->addr->hash != UNIX_HASH_SIZE) +#ifdef CONFIG_SECURITY_NETWORK +static void unix_get_peersec_dgram(struct sk_buff *skb) +{ + int err; + + err = security_socket_getpeersec_dgram(skb, UNIXSECDATA(skb), + UNIXSECLEN(skb)); + if (err) + *(UNIXSECDATA(skb)) = NULL; +} + +static inline void unix_set_secdata(struct scm_cookie *scm, struct sk_buff *skb) +{ + scm->secdata = *UNIXSECDATA(skb); + scm->seclen = *UNIXSECLEN(skb); +} +#else +static void unix_get_peersec_dgram(struct sk_buff *skb) +{ } + +static inline void unix_set_secdata(struct scm_cookie *scm, struct sk_buff *skb) +{ } +#endif /* CONFIG_SECURITY_NETWORK */ + /* * SMP locking strategy: * hash table is protected with spinlock unix_table_lock @@ -1291,6 +1315,8 @@ static int unix_dgram_sendmsg(struct kiocb *kiocb, struct socket *sock, if (siocb->scm->fp) unix_attach_fds(siocb->scm, skb); + unix_get_peersec_dgram(skb); + skb->h.raw = skb->data; err = memcpy_fromiovec(skb_put(skb,len), msg->msg_iov, len); if (err) @@ -1570,6 +1596,7 @@ static int unix_dgram_recvmsg(struct kiocb *iocb, struct socket *sock, memset(&tmp_scm, 0, sizeof(tmp_scm)); } siocb->scm->creds = *UNIXCREDS(skb); + unix_set_secdata(siocb->scm, skb); if (!(flags & MSG_PEEK)) { |