1c66b4d8dSRobert Watson /*-
25c95417dSRobert Watson * Copyright (c) 1999-2002, 2007, 2009, 2019 Robert N. M. Watson
3c66b4d8dSRobert Watson * Copyright (c) 2001 Ilmar S. Habibulin
4c66b4d8dSRobert Watson * Copyright (c) 2001-2004 Networks Associates Technology, Inc.
530d239bcSRobert Watson * Copyright (c) 2006 SPARTA, Inc.
66356dba0SRobert Watson * Copyright (c) 2008 Apple Inc.
7c66b4d8dSRobert Watson * All rights reserved.
8c66b4d8dSRobert Watson *
9c66b4d8dSRobert Watson * This software was developed by Robert Watson and Ilmar Habibulin for the
10c66b4d8dSRobert Watson * TrustedBSD Project.
11c66b4d8dSRobert Watson *
12c66b4d8dSRobert Watson * This software was developed for the FreeBSD Project in part by Network
13c66b4d8dSRobert Watson * Associates Laboratories, the Security Research Division of Network
14c66b4d8dSRobert Watson * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 ("CBOSS"),
15c66b4d8dSRobert Watson * as part of the DARPA CHATS research program.
16c66b4d8dSRobert Watson *
1730d239bcSRobert Watson * This software was enhanced by SPARTA ISSO under SPAWAR contract
1830d239bcSRobert Watson * N66001-04-C-6019 ("SEFOS").
1930d239bcSRobert Watson *
202087a58cSRobert Watson * This software was developed at the University of Cambridge Computer
212087a58cSRobert Watson * Laboratory with support from a grant from Google, Inc.
222087a58cSRobert Watson *
23c66b4d8dSRobert Watson * Redistribution and use in source and binary forms, with or without
24c66b4d8dSRobert Watson * modification, are permitted provided that the following conditions
25c66b4d8dSRobert Watson * are met:
26c66b4d8dSRobert Watson * 1. Redistributions of source code must retain the above copyright
27c66b4d8dSRobert Watson * notice, this list of conditions and the following disclaimer.
28c66b4d8dSRobert Watson * 2. Redistributions in binary form must reproduce the above copyright
29c66b4d8dSRobert Watson * notice, this list of conditions and the following disclaimer in the
30c66b4d8dSRobert Watson * documentation and/or other materials provided with the distribution.
31c66b4d8dSRobert Watson *
32c66b4d8dSRobert Watson * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
33c66b4d8dSRobert Watson * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
34c66b4d8dSRobert Watson * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
35c66b4d8dSRobert Watson * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
36c66b4d8dSRobert Watson * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
37c66b4d8dSRobert Watson * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
38c66b4d8dSRobert Watson * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
39c66b4d8dSRobert Watson * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
40c66b4d8dSRobert Watson * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
41c66b4d8dSRobert Watson * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
42c66b4d8dSRobert Watson * SUCH DAMAGE.
43c66b4d8dSRobert Watson */
44c66b4d8dSRobert Watson
45c66b4d8dSRobert Watson #include <sys/cdefs.h>
46c66b4d8dSRobert Watson #include "opt_mac.h"
47c66b4d8dSRobert Watson
48c66b4d8dSRobert Watson #include <sys/param.h>
49c66b4d8dSRobert Watson #include <sys/kernel.h>
50c66b4d8dSRobert Watson #include <sys/lock.h>
51c66b4d8dSRobert Watson #include <sys/malloc.h>
52c66b4d8dSRobert Watson #include <sys/mutex.h>
53c66b4d8dSRobert Watson #include <sys/sbuf.h>
542087a58cSRobert Watson #include <sys/sdt.h>
55c66b4d8dSRobert Watson #include <sys/systm.h>
56c66b4d8dSRobert Watson #include <sys/mount.h>
57c66b4d8dSRobert Watson #include <sys/file.h>
58c66b4d8dSRobert Watson #include <sys/namei.h>
59c66b4d8dSRobert Watson #include <sys/protosw.h>
60c66b4d8dSRobert Watson #include <sys/socket.h>
61c66b4d8dSRobert Watson #include <sys/socketvar.h>
62c66b4d8dSRobert Watson #include <sys/sysctl.h>
63c66b4d8dSRobert Watson
64c66b4d8dSRobert Watson #include <net/if.h>
65c66b4d8dSRobert Watson #include <net/if_var.h>
66c66b4d8dSRobert Watson
67c66b4d8dSRobert Watson #include <netinet/in.h>
68c66b4d8dSRobert Watson #include <netinet/in_pcb.h>
69c66b4d8dSRobert Watson #include <netinet/ip_var.h>
70c66b4d8dSRobert Watson
71aed55708SRobert Watson #include <security/mac/mac_framework.h>
72c66b4d8dSRobert Watson #include <security/mac/mac_internal.h>
730efd6615SRobert Watson #include <security/mac/mac_policy.h>
74c66b4d8dSRobert Watson
75c66b4d8dSRobert Watson static struct label *
mac_inpcb_label_alloc(int flag)76c66b4d8dSRobert Watson mac_inpcb_label_alloc(int flag)
77c66b4d8dSRobert Watson {
78c66b4d8dSRobert Watson struct label *label;
79c66b4d8dSRobert Watson int error;
80c66b4d8dSRobert Watson
81c66b4d8dSRobert Watson label = mac_labelzone_alloc(flag);
82c66b4d8dSRobert Watson if (label == NULL)
83c66b4d8dSRobert Watson return (NULL);
8440202729SRobert Watson if (flag & M_WAITOK)
85fa765671SRobert Watson MAC_POLICY_CHECK(inpcb_init_label, label, flag);
8640202729SRobert Watson else
87fa765671SRobert Watson MAC_POLICY_CHECK_NOSLEEP(inpcb_init_label, label, flag);
88c66b4d8dSRobert Watson if (error) {
89fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(inpcb_destroy_label, label);
90c66b4d8dSRobert Watson mac_labelzone_free(label);
91c66b4d8dSRobert Watson return (NULL);
92c66b4d8dSRobert Watson }
93c66b4d8dSRobert Watson return (label);
94c66b4d8dSRobert Watson }
95c66b4d8dSRobert Watson
96c66b4d8dSRobert Watson int
mac_inpcb_init(struct inpcb * inp,int flag)9730d239bcSRobert Watson mac_inpcb_init(struct inpcb *inp, int flag)
98c66b4d8dSRobert Watson {
99c66b4d8dSRobert Watson
1006356dba0SRobert Watson if (mac_labeled & MPC_OBJECT_INPCB) {
101c66b4d8dSRobert Watson inp->inp_label = mac_inpcb_label_alloc(flag);
102c66b4d8dSRobert Watson if (inp->inp_label == NULL)
103c66b4d8dSRobert Watson return (ENOMEM);
1046356dba0SRobert Watson } else
1056356dba0SRobert Watson inp->inp_label = NULL;
106c66b4d8dSRobert Watson return (0);
107c66b4d8dSRobert Watson }
108c66b4d8dSRobert Watson
109215bab79SShivank Garg /* Check with rules in module if the IPv4 address is allowed. */
110215bab79SShivank Garg int
mac_inet_check_add_addr(struct ucred * cred,const struct in_addr * ia,struct ifnet * ifp)111215bab79SShivank Garg mac_inet_check_add_addr(struct ucred *cred, const struct in_addr *ia,
112215bab79SShivank Garg struct ifnet *ifp)
113215bab79SShivank Garg {
114215bab79SShivank Garg int error;
115215bab79SShivank Garg
116215bab79SShivank Garg MAC_POLICY_CHECK(ip4_check_jail, cred, ia, ifp);
117215bab79SShivank Garg return (error);
118215bab79SShivank Garg }
119215bab79SShivank Garg
120c66b4d8dSRobert Watson static struct label *
mac_ipq_label_alloc(int flag)121c66b4d8dSRobert Watson mac_ipq_label_alloc(int flag)
122c66b4d8dSRobert Watson {
123c66b4d8dSRobert Watson struct label *label;
124c66b4d8dSRobert Watson int error;
125c66b4d8dSRobert Watson
126c66b4d8dSRobert Watson label = mac_labelzone_alloc(flag);
127c66b4d8dSRobert Watson if (label == NULL)
128c66b4d8dSRobert Watson return (NULL);
129c66b4d8dSRobert Watson
13040202729SRobert Watson if (flag & M_WAITOK)
131fa765671SRobert Watson MAC_POLICY_CHECK(ipq_init_label, label, flag);
13240202729SRobert Watson else
133fa765671SRobert Watson MAC_POLICY_CHECK_NOSLEEP(ipq_init_label, label, flag);
134c66b4d8dSRobert Watson if (error) {
135fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(ipq_destroy_label, label);
136c66b4d8dSRobert Watson mac_labelzone_free(label);
137c66b4d8dSRobert Watson return (NULL);
138c66b4d8dSRobert Watson }
139c66b4d8dSRobert Watson return (label);
140c66b4d8dSRobert Watson }
141c66b4d8dSRobert Watson
142c66b4d8dSRobert Watson int
mac_ipq_init(struct ipq * q,int flag)14337f44cb4SRobert Watson mac_ipq_init(struct ipq *q, int flag)
144c66b4d8dSRobert Watson {
145c66b4d8dSRobert Watson
1466356dba0SRobert Watson if (mac_labeled & MPC_OBJECT_IPQ) {
14737f44cb4SRobert Watson q->ipq_label = mac_ipq_label_alloc(flag);
14837f44cb4SRobert Watson if (q->ipq_label == NULL)
149c66b4d8dSRobert Watson return (ENOMEM);
1506356dba0SRobert Watson } else
1516356dba0SRobert Watson q->ipq_label = NULL;
152c66b4d8dSRobert Watson return (0);
153c66b4d8dSRobert Watson }
154c66b4d8dSRobert Watson
155c66b4d8dSRobert Watson static void
mac_inpcb_label_free(struct label * label)156c66b4d8dSRobert Watson mac_inpcb_label_free(struct label *label)
157c66b4d8dSRobert Watson {
158c66b4d8dSRobert Watson
159fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(inpcb_destroy_label, label);
160c66b4d8dSRobert Watson mac_labelzone_free(label);
161c66b4d8dSRobert Watson }
162c66b4d8dSRobert Watson
163c66b4d8dSRobert Watson void
mac_inpcb_destroy(struct inpcb * inp)16430d239bcSRobert Watson mac_inpcb_destroy(struct inpcb *inp)
165c66b4d8dSRobert Watson {
166c66b4d8dSRobert Watson
1676356dba0SRobert Watson if (inp->inp_label != NULL) {
168c66b4d8dSRobert Watson mac_inpcb_label_free(inp->inp_label);
169c66b4d8dSRobert Watson inp->inp_label = NULL;
170c66b4d8dSRobert Watson }
1716356dba0SRobert Watson }
172c66b4d8dSRobert Watson
173c66b4d8dSRobert Watson static void
mac_ipq_label_free(struct label * label)174c66b4d8dSRobert Watson mac_ipq_label_free(struct label *label)
175c66b4d8dSRobert Watson {
176c66b4d8dSRobert Watson
177fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(ipq_destroy_label, label);
178c66b4d8dSRobert Watson mac_labelzone_free(label);
179c66b4d8dSRobert Watson }
180c66b4d8dSRobert Watson
181c66b4d8dSRobert Watson void
mac_ipq_destroy(struct ipq * q)18237f44cb4SRobert Watson mac_ipq_destroy(struct ipq *q)
183c66b4d8dSRobert Watson {
184c66b4d8dSRobert Watson
1856356dba0SRobert Watson if (q->ipq_label != NULL) {
18637f44cb4SRobert Watson mac_ipq_label_free(q->ipq_label);
18737f44cb4SRobert Watson q->ipq_label = NULL;
188c66b4d8dSRobert Watson }
1896356dba0SRobert Watson }
190c66b4d8dSRobert Watson
191c66b4d8dSRobert Watson void
mac_inpcb_create(struct socket * so,struct inpcb * inp)19230d239bcSRobert Watson mac_inpcb_create(struct socket *so, struct inpcb *inp)
193c66b4d8dSRobert Watson {
194c66b4d8dSRobert Watson
195fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(inpcb_create, so, so->so_label, inp,
19640202729SRobert Watson inp->inp_label);
197c66b4d8dSRobert Watson }
198c66b4d8dSRobert Watson
199c66b4d8dSRobert Watson void
mac_ipq_reassemble(struct ipq * q,struct mbuf * m)20037f44cb4SRobert Watson mac_ipq_reassemble(struct ipq *q, struct mbuf *m)
201c66b4d8dSRobert Watson {
202c66b4d8dSRobert Watson struct label *label;
203c66b4d8dSRobert Watson
2043de40469SRobert Watson if (mac_policy_count == 0)
2053de40469SRobert Watson return;
2063de40469SRobert Watson
20726ae2b86SRobert Watson label = mac_mbuf_to_label(m);
208c66b4d8dSRobert Watson
209fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(ipq_reassemble, q, q->ipq_label, m,
210fa765671SRobert Watson label);
211c66b4d8dSRobert Watson }
212c66b4d8dSRobert Watson
213c66b4d8dSRobert Watson void
mac_netinet_fragment(struct mbuf * m,struct mbuf * frag)21430d239bcSRobert Watson mac_netinet_fragment(struct mbuf *m, struct mbuf *frag)
215c66b4d8dSRobert Watson {
21626ae2b86SRobert Watson struct label *mlabel, *fraglabel;
217c66b4d8dSRobert Watson
2183de40469SRobert Watson if (mac_policy_count == 0)
2193de40469SRobert Watson return;
2203de40469SRobert Watson
22126ae2b86SRobert Watson mlabel = mac_mbuf_to_label(m);
22226ae2b86SRobert Watson fraglabel = mac_mbuf_to_label(frag);
223c66b4d8dSRobert Watson
224fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(netinet_fragment, m, mlabel, frag,
225fa765671SRobert Watson fraglabel);
226c66b4d8dSRobert Watson }
227c66b4d8dSRobert Watson
228c66b4d8dSRobert Watson void
mac_ipq_create(struct mbuf * m,struct ipq * q)22937f44cb4SRobert Watson mac_ipq_create(struct mbuf *m, struct ipq *q)
230c66b4d8dSRobert Watson {
231c66b4d8dSRobert Watson struct label *label;
232c66b4d8dSRobert Watson
2333de40469SRobert Watson if (mac_policy_count == 0)
2343de40469SRobert Watson return;
2353de40469SRobert Watson
23626ae2b86SRobert Watson label = mac_mbuf_to_label(m);
237c66b4d8dSRobert Watson
238fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(ipq_create, m, label, q, q->ipq_label);
239c66b4d8dSRobert Watson }
240c66b4d8dSRobert Watson
241c66b4d8dSRobert Watson void
mac_inpcb_create_mbuf(struct inpcb * inp,struct mbuf * m)24230d239bcSRobert Watson mac_inpcb_create_mbuf(struct inpcb *inp, struct mbuf *m)
243c66b4d8dSRobert Watson {
244c66b4d8dSRobert Watson struct label *mlabel;
245c66b4d8dSRobert Watson
246211b72adSRobert Watson INP_LOCK_ASSERT(inp);
2473de40469SRobert Watson
2483de40469SRobert Watson if (mac_policy_count == 0)
2493de40469SRobert Watson return;
2503de40469SRobert Watson
251c66b4d8dSRobert Watson mlabel = mac_mbuf_to_label(m);
252c66b4d8dSRobert Watson
253fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(inpcb_create_mbuf, inp, inp->inp_label, m,
25440202729SRobert Watson mlabel);
255c66b4d8dSRobert Watson }
256c66b4d8dSRobert Watson
257c66b4d8dSRobert Watson int
mac_ipq_match(struct mbuf * m,struct ipq * q)25837f44cb4SRobert Watson mac_ipq_match(struct mbuf *m, struct ipq *q)
259c66b4d8dSRobert Watson {
260c66b4d8dSRobert Watson struct label *label;
261c66b4d8dSRobert Watson int result;
262c66b4d8dSRobert Watson
2633de40469SRobert Watson if (mac_policy_count == 0)
2643de40469SRobert Watson return (1);
2653de40469SRobert Watson
26626ae2b86SRobert Watson label = mac_mbuf_to_label(m);
267c66b4d8dSRobert Watson
268c66b4d8dSRobert Watson result = 1;
269fa765671SRobert Watson MAC_POLICY_BOOLEAN_NOSLEEP(ipq_match, &&, m, label, q, q->ipq_label);
270c66b4d8dSRobert Watson
271c66b4d8dSRobert Watson return (result);
272c66b4d8dSRobert Watson }
273c66b4d8dSRobert Watson
274c66b4d8dSRobert Watson void
mac_netinet_arp_send(struct ifnet * ifp,struct mbuf * m)275b9b0dac3SRobert Watson mac_netinet_arp_send(struct ifnet *ifp, struct mbuf *m)
276b9b0dac3SRobert Watson {
277b9b0dac3SRobert Watson struct label *mlabel;
2785c95417dSRobert Watson int locked;
279b9b0dac3SRobert Watson
2803de40469SRobert Watson if (mac_policy_count == 0)
2813de40469SRobert Watson return;
2823de40469SRobert Watson
283b9b0dac3SRobert Watson mlabel = mac_mbuf_to_label(m);
284b9b0dac3SRobert Watson
2855c95417dSRobert Watson MAC_IFNET_LOCK(ifp, locked);
28630af2c13SJustin Hibbits MAC_POLICY_PERFORM_NOSLEEP(netinet_arp_send, ifp, if_getmaclabel(ifp),
28730af2c13SJustin Hibbits m, mlabel);
2885c95417dSRobert Watson MAC_IFNET_UNLOCK(ifp, locked);
289b9b0dac3SRobert Watson }
290b9b0dac3SRobert Watson
291b9b0dac3SRobert Watson void
mac_netinet_icmp_reply(struct mbuf * mrecv,struct mbuf * msend)292a13e21f7SRobert Watson mac_netinet_icmp_reply(struct mbuf *mrecv, struct mbuf *msend)
293a13e21f7SRobert Watson {
294a13e21f7SRobert Watson struct label *mrecvlabel, *msendlabel;
295a13e21f7SRobert Watson
2963de40469SRobert Watson if (mac_policy_count == 0)
2973de40469SRobert Watson return;
2983de40469SRobert Watson
299a13e21f7SRobert Watson mrecvlabel = mac_mbuf_to_label(mrecv);
300a13e21f7SRobert Watson msendlabel = mac_mbuf_to_label(msend);
301a13e21f7SRobert Watson
302fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(netinet_icmp_reply, mrecv, mrecvlabel,
303fa765671SRobert Watson msend, msendlabel);
304a13e21f7SRobert Watson }
305a13e21f7SRobert Watson
306a13e21f7SRobert Watson void
mac_netinet_icmp_replyinplace(struct mbuf * m)307a13e21f7SRobert Watson mac_netinet_icmp_replyinplace(struct mbuf *m)
308c66b4d8dSRobert Watson {
309c66b4d8dSRobert Watson struct label *label;
310c66b4d8dSRobert Watson
3113de40469SRobert Watson if (mac_policy_count == 0)
3123de40469SRobert Watson return;
3133de40469SRobert Watson
314c66b4d8dSRobert Watson label = mac_mbuf_to_label(m);
315c66b4d8dSRobert Watson
316fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(netinet_icmp_replyinplace, m, label);
317c66b4d8dSRobert Watson }
31826ae2b86SRobert Watson
319c66b4d8dSRobert Watson void
mac_netinet_igmp_send(struct ifnet * ifp,struct mbuf * m)320b9b0dac3SRobert Watson mac_netinet_igmp_send(struct ifnet *ifp, struct mbuf *m)
321b9b0dac3SRobert Watson {
322b9b0dac3SRobert Watson struct label *mlabel;
3235c95417dSRobert Watson int locked;
324b9b0dac3SRobert Watson
3253de40469SRobert Watson if (mac_policy_count == 0)
3263de40469SRobert Watson return;
3273de40469SRobert Watson
328b9b0dac3SRobert Watson mlabel = mac_mbuf_to_label(m);
329b9b0dac3SRobert Watson
3305c95417dSRobert Watson MAC_IFNET_LOCK(ifp, locked);
33130af2c13SJustin Hibbits MAC_POLICY_PERFORM_NOSLEEP(netinet_igmp_send, ifp, if_getmaclabel(ifp),
33230af2c13SJustin Hibbits m, mlabel);
3335c95417dSRobert Watson MAC_IFNET_UNLOCK(ifp, locked);
334b9b0dac3SRobert Watson }
335b9b0dac3SRobert Watson
336b9b0dac3SRobert Watson void
mac_netinet_tcp_reply(struct mbuf * m)33730d239bcSRobert Watson mac_netinet_tcp_reply(struct mbuf *m)
338c66b4d8dSRobert Watson {
339c66b4d8dSRobert Watson struct label *label;
340c66b4d8dSRobert Watson
3413de40469SRobert Watson if (mac_policy_count == 0)
3423de40469SRobert Watson return;
3433de40469SRobert Watson
344c66b4d8dSRobert Watson label = mac_mbuf_to_label(m);
345c66b4d8dSRobert Watson
346fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(netinet_tcp_reply, m, label);
347c66b4d8dSRobert Watson }
348c66b4d8dSRobert Watson
349c66b4d8dSRobert Watson void
mac_ipq_update(struct mbuf * m,struct ipq * q)35037f44cb4SRobert Watson mac_ipq_update(struct mbuf *m, struct ipq *q)
351c66b4d8dSRobert Watson {
352c66b4d8dSRobert Watson struct label *label;
353c66b4d8dSRobert Watson
3543de40469SRobert Watson if (mac_policy_count == 0)
3553de40469SRobert Watson return;
3563de40469SRobert Watson
35726ae2b86SRobert Watson label = mac_mbuf_to_label(m);
358c66b4d8dSRobert Watson
359fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(ipq_update, m, label, q, q->ipq_label);
360c66b4d8dSRobert Watson }
361c66b4d8dSRobert Watson
3622087a58cSRobert Watson MAC_CHECK_PROBE_DEFINE2(inpcb_check_deliver, "struct inpcb *",
3632087a58cSRobert Watson "struct mbuf *");
3642087a58cSRobert Watson
365c66b4d8dSRobert Watson int
mac_inpcb_check_deliver(struct inpcb * inp,struct mbuf * m)36630d239bcSRobert Watson mac_inpcb_check_deliver(struct inpcb *inp, struct mbuf *m)
367c66b4d8dSRobert Watson {
368c66b4d8dSRobert Watson struct label *label;
369c66b4d8dSRobert Watson int error;
370c66b4d8dSRobert Watson
371c66b4d8dSRobert Watson M_ASSERTPKTHDR(m);
372c66b4d8dSRobert Watson
3733de40469SRobert Watson if (mac_policy_count == 0)
3743de40469SRobert Watson return (0);
3753de40469SRobert Watson
376c66b4d8dSRobert Watson label = mac_mbuf_to_label(m);
377c66b4d8dSRobert Watson
378fa765671SRobert Watson MAC_POLICY_CHECK_NOSLEEP(inpcb_check_deliver, inp, inp->inp_label, m,
37940202729SRobert Watson label);
3802087a58cSRobert Watson MAC_CHECK_PROBE2(inpcb_check_deliver, error, inp, m);
381c66b4d8dSRobert Watson
382c66b4d8dSRobert Watson return (error);
383c66b4d8dSRobert Watson }
384c66b4d8dSRobert Watson
3852087a58cSRobert Watson MAC_CHECK_PROBE_DEFINE2(inpcb_check_visible, "struct ucred *",
3862087a58cSRobert Watson "struct inpcb *");
3872087a58cSRobert Watson
38837ee7293SBjoern A. Zeeb int
mac_inpcb_check_visible(struct ucred * cred,struct inpcb * inp)38937ee7293SBjoern A. Zeeb mac_inpcb_check_visible(struct ucred *cred, struct inpcb *inp)
39037ee7293SBjoern A. Zeeb {
39137ee7293SBjoern A. Zeeb int error;
39237ee7293SBjoern A. Zeeb
39337ee7293SBjoern A. Zeeb INP_LOCK_ASSERT(inp);
39437ee7293SBjoern A. Zeeb
395fa765671SRobert Watson MAC_POLICY_CHECK_NOSLEEP(inpcb_check_visible, cred, inp,
396fa765671SRobert Watson inp->inp_label);
3972087a58cSRobert Watson MAC_CHECK_PROBE2(inpcb_check_visible, error, cred, inp);
39837ee7293SBjoern A. Zeeb
39937ee7293SBjoern A. Zeeb return (error);
40037ee7293SBjoern A. Zeeb }
40137ee7293SBjoern A. Zeeb
402c66b4d8dSRobert Watson void
mac_inpcb_sosetlabel(struct socket * so,struct inpcb * inp)403c66b4d8dSRobert Watson mac_inpcb_sosetlabel(struct socket *so, struct inpcb *inp)
404c66b4d8dSRobert Watson {
405c66b4d8dSRobert Watson
4068501a69cSRobert Watson INP_WLOCK_ASSERT(inp);
407c982ffa4SRobert Watson SOCK_LOCK_ASSERT(so);
40840202729SRobert Watson
409fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(inpcb_sosetlabel, so, so->so_label, inp,
41040202729SRobert Watson inp->inp_label);
411c66b4d8dSRobert Watson }
412d94f2a68SChristian S.J. Peron
413d94f2a68SChristian S.J. Peron void
mac_netinet_firewall_reply(struct mbuf * mrecv,struct mbuf * msend)414a13e21f7SRobert Watson mac_netinet_firewall_reply(struct mbuf *mrecv, struct mbuf *msend)
415a13e21f7SRobert Watson {
416a13e21f7SRobert Watson struct label *mrecvlabel, *msendlabel;
417a13e21f7SRobert Watson
418a13e21f7SRobert Watson M_ASSERTPKTHDR(mrecv);
419a13e21f7SRobert Watson M_ASSERTPKTHDR(msend);
420a13e21f7SRobert Watson
4213de40469SRobert Watson if (mac_policy_count == 0)
4223de40469SRobert Watson return;
4233de40469SRobert Watson
424a13e21f7SRobert Watson mrecvlabel = mac_mbuf_to_label(mrecv);
425a13e21f7SRobert Watson msendlabel = mac_mbuf_to_label(msend);
426a13e21f7SRobert Watson
427fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(netinet_firewall_reply, mrecv, mrecvlabel,
428fa765671SRobert Watson msend, msendlabel);
429a13e21f7SRobert Watson }
430a13e21f7SRobert Watson
431a13e21f7SRobert Watson void
mac_netinet_firewall_send(struct mbuf * m)43286407646SRobert Watson mac_netinet_firewall_send(struct mbuf *m)
433d94f2a68SChristian S.J. Peron {
434d94f2a68SChristian S.J. Peron struct label *label;
435d94f2a68SChristian S.J. Peron
436d94f2a68SChristian S.J. Peron M_ASSERTPKTHDR(m);
43740202729SRobert Watson
4383de40469SRobert Watson if (mac_policy_count == 0)
4393de40469SRobert Watson return;
4403de40469SRobert Watson
441d94f2a68SChristian S.J. Peron label = mac_mbuf_to_label(m);
44240202729SRobert Watson
443fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(netinet_firewall_send, m, label);
444d94f2a68SChristian S.J. Peron }
445826cef3dSChristian S.J. Peron
446826cef3dSChristian S.J. Peron /*
44795c8c170SRobert Watson * These functions really should be referencing the syncache structure
44895c8c170SRobert Watson * instead of the label. However, due to some of the complexities associated
44928323addSBryan Drewery * with exposing this syncache structure we operate directly on its label
45095c8c170SRobert Watson * pointer. This should be OK since we aren't making any access control
45195c8c170SRobert Watson * decisions within this code directly, we are merely allocating and copying
45295c8c170SRobert Watson * label storage so we can properly initialize mbuf labels for any packets
45395c8c170SRobert Watson * the syncache code might create.
454826cef3dSChristian S.J. Peron */
455826cef3dSChristian S.J. Peron void
mac_syncache_destroy(struct label ** label)45602be6269SRobert Watson mac_syncache_destroy(struct label **label)
457826cef3dSChristian S.J. Peron {
458826cef3dSChristian S.J. Peron
4596356dba0SRobert Watson if (*label != NULL) {
460fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(syncache_destroy_label, *label);
461826cef3dSChristian S.J. Peron mac_labelzone_free(*label);
462826cef3dSChristian S.J. Peron *label = NULL;
463826cef3dSChristian S.J. Peron }
4646356dba0SRobert Watson }
465826cef3dSChristian S.J. Peron
466826cef3dSChristian S.J. Peron int
mac_syncache_init(struct label ** label)46702be6269SRobert Watson mac_syncache_init(struct label **label)
468826cef3dSChristian S.J. Peron {
469826cef3dSChristian S.J. Peron int error;
470826cef3dSChristian S.J. Peron
4716356dba0SRobert Watson if (mac_labeled & MPC_OBJECT_SYNCACHE) {
472826cef3dSChristian S.J. Peron *label = mac_labelzone_alloc(M_NOWAIT);
473826cef3dSChristian S.J. Peron if (*label == NULL)
474826cef3dSChristian S.J. Peron return (ENOMEM);
475826cef3dSChristian S.J. Peron /*
4766356dba0SRobert Watson * Since we are holding the inpcb locks the policy can not
4776356dba0SRobert Watson * allocate policy specific label storage using M_WAITOK. So
4786356dba0SRobert Watson * we need to do a MAC_CHECK instead of the typical
4796356dba0SRobert Watson * MAC_PERFORM so we can propagate allocation failures back
4806356dba0SRobert Watson * to the syncache code.
481826cef3dSChristian S.J. Peron */
482fa765671SRobert Watson MAC_POLICY_CHECK_NOSLEEP(syncache_init_label, *label,
483fa765671SRobert Watson M_NOWAIT);
4841f84ab0fSChristian S.J. Peron if (error) {
485fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(syncache_destroy_label,
486fa765671SRobert Watson *label);
4871f84ab0fSChristian S.J. Peron mac_labelzone_free(*label);
488*3f279216SMichael Tuexen *label = NULL;
4891f84ab0fSChristian S.J. Peron }
490826cef3dSChristian S.J. Peron return (error);
4916356dba0SRobert Watson } else
4926356dba0SRobert Watson *label = NULL;
4936356dba0SRobert Watson return (0);
494826cef3dSChristian S.J. Peron }
495826cef3dSChristian S.J. Peron
496826cef3dSChristian S.J. Peron void
mac_syncache_create(struct label * label,struct inpcb * inp)49702be6269SRobert Watson mac_syncache_create(struct label *label, struct inpcb *inp)
498826cef3dSChristian S.J. Peron {
499826cef3dSChristian S.J. Peron
50008d9c920SGleb Smirnoff INP_LOCK_ASSERT(inp);
50140202729SRobert Watson
502fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(syncache_create, label, inp);
503826cef3dSChristian S.J. Peron }
504826cef3dSChristian S.J. Peron
505826cef3dSChristian S.J. Peron void
mac_syncache_create_mbuf(struct label * sc_label,struct mbuf * m)50602be6269SRobert Watson mac_syncache_create_mbuf(struct label *sc_label, struct mbuf *m)
507826cef3dSChristian S.J. Peron {
50826ae2b86SRobert Watson struct label *mlabel;
509826cef3dSChristian S.J. Peron
510826cef3dSChristian S.J. Peron M_ASSERTPKTHDR(m);
51140202729SRobert Watson
5123de40469SRobert Watson if (mac_policy_count == 0)
5133de40469SRobert Watson return;
5143de40469SRobert Watson
51526ae2b86SRobert Watson mlabel = mac_mbuf_to_label(m);
51640202729SRobert Watson
517fa765671SRobert Watson MAC_POLICY_PERFORM_NOSLEEP(syncache_create_mbuf, sc_label, m,
518fa765671SRobert Watson mlabel);
519826cef3dSChristian S.J. Peron }
520