/** * selinux_netlbl_inode_permission - Verify the socket is NetLabel labeled * @inode: the file descriptor's inode * @mask: the permission mask * * Description: * Looks at a file's inode and if it is marked as a socket protected by * NetLabel then verify that the socket has been labeled, if not try to label * the socket now with the inode's SID. Returns zero on success, negative * values on failure. * */ int selinux_netlbl_inode_permission(struct inode *inode, int mask) { int rc; struct sock *sk; struct socket *sock; struct sk_security_struct *sksec; if (!S_ISSOCK(inode->i_mode) || ((mask & (MAY_WRITE | MAY_APPEND)) == 0)) return 0; sock = SOCKET_I(inode); sk = sock->sk; sksec = sk->sk_security; if (sksec->nlbl_state != NLBL_REQUIRE) return 0; local_bh_disable(); bh_lock_sock_nested(sk); if (likely(sksec->nlbl_state == NLBL_REQUIRE)) rc = selinux_netlbl_sock_setsid(sk); else rc = 0; bh_unlock_sock(sk); local_bh_enable(); return rc; }
/** * selinux_netlbl_sock_graft - Netlabel the new socket * @sk: the new connection * @sock: the new socket * * Description: * The connection represented by @sk is being grafted onto @sock so set the * socket's NetLabel to match the SID of @sk. * */ void selinux_netlbl_sock_graft(struct sock *sk, struct socket *sock) { struct sk_security_struct *sksec = sk->sk_security; struct netlbl_lsm_secattr secattr; u32 nlbl_peer_sid; rcu_read_lock(); if (sksec->nlbl_state != NLBL_REQUIRE) { rcu_read_unlock(); return; } netlbl_secattr_init(&secattr); if (netlbl_sock_getattr(sk, &secattr) == 0 && secattr.flags != NETLBL_SECATTR_NONE && security_netlbl_secattr_to_sid(&secattr, &nlbl_peer_sid) == 0) sksec->peer_sid = nlbl_peer_sid; netlbl_secattr_destroy(&secattr); /* Try to set the NetLabel on the socket to save time later, if we fail * here we will pick up the pieces in later calls to * selinux_netlbl_inode_permission(). */ selinux_netlbl_sock_setsid(sk, sksec->sid); rcu_read_unlock(); }
/** * selinux_netlbl_socket_post_create - Label a socket using NetLabel * @sock: the socket to label * * Description: * Attempt to label a socket using the NetLabel mechanism using the given * SID. Returns zero values on success, negative values on failure. * */ int selinux_netlbl_socket_post_create(struct socket *sock) { int rc = 0; struct sock *sk = sock->sk; struct sk_security_struct *sksec = sk->sk_security; rcu_read_lock(); if (sksec->nlbl_state == NLBL_REQUIRE) rc = selinux_netlbl_sock_setsid(sk, sksec->sid); rcu_read_unlock(); return rc; }
/** * selinux_netlbl_socket_post_create - Label a socket using NetLabel * @sock: the socket to label * * Description: * Attempt to label a socket using the NetLabel mechanism using the given * SID. Returns zero values on success, negative values on failure. * */ int selinux_netlbl_socket_post_create(struct socket *sock) { return selinux_netlbl_sock_setsid(sock->sk); }