mac_biba.c revision 103750
1/*-
2 * Copyright (c) 1999, 2000, 2001, 2002 Robert N. M. Watson
3 * Copyright (c) 2001, 2002 Networks Associates Technology, Inc.
4 * All rights reserved.
5 *
6 * This software was developed by Robert Watson for the TrustedBSD Project.
7 *
8 * This software was developed for the FreeBSD Project in part by NAI Labs,
9 * the Security Research Division of Network Associates, Inc. under
10 * DARPA/SPAWAR contract N66001-01-C-8035 ("CBOSS"), as part of the DARPA
11 * CHATS research program.
12 *
13 * Redistribution and use in source and binary forms, with or without
14 * modification, are permitted provided that the following conditions
15 * are met:
16 * 1. Redistributions of source code must retain the above copyright
17 *    notice, this list of conditions and the following disclaimer.
18 * 2. Redistributions in binary form must reproduce the above copyright
19 *    notice, this list of conditions and the following disclaimer in the
20 *    documentation and/or other materials provided with the distribution.
21 * 3. The names of the authors may not be used to endorse or promote
22 *    products derived from this software without specific prior written
23 *    permission.
24 *
25 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
26 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
27 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
28 * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
29 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
30 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
31 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
32 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
33 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
34 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
35 * SUCH DAMAGE.
36 *
37 * $FreeBSD: head/sys/security/mac_biba/mac_biba.c 103750 2002-09-21 18:29:37Z rwatson $
38 */
39
40/*
41 * Developed by the TrustedBSD Project.
42 * Biba fixed label mandatory integrity policy.
43 */
44
45#include <sys/types.h>
46#include <sys/param.h>
47#include <sys/acl.h>
48#include <sys/conf.h>
49#include <sys/kernel.h>
50#include <sys/mac.h>
51#include <sys/malloc.h>
52#include <sys/mount.h>
53#include <sys/proc.h>
54#include <sys/systm.h>
55#include <sys/sysproto.h>
56#include <sys/sysent.h>
57#include <sys/vnode.h>
58#include <sys/file.h>
59#include <sys/socket.h>
60#include <sys/socketvar.h>
61#include <sys/pipe.h>
62#include <sys/sysctl.h>
63
64#include <fs/devfs/devfs.h>
65
66#include <net/bpfdesc.h>
67#include <net/if.h>
68#include <net/if_types.h>
69#include <net/if_var.h>
70
71#include <netinet/in.h>
72#include <netinet/ip_var.h>
73
74#include <vm/vm.h>
75
76#include <sys/mac_policy.h>
77
78#include <security/mac_biba/mac_biba.h>
79
80SYSCTL_DECL(_security_mac);
81
82SYSCTL_NODE(_security_mac, OID_AUTO, biba, CTLFLAG_RW, 0,
83    "TrustedBSD mac_biba policy controls");
84
85static int	mac_biba_enabled = 0;
86SYSCTL_INT(_security_mac_biba, OID_AUTO, enabled, CTLFLAG_RW,
87    &mac_biba_enabled, 0, "Enforce MAC/Biba policy");
88TUNABLE_INT("security.mac.biba.enabled", &mac_biba_enabled);
89
90static int	destroyed_not_inited;
91SYSCTL_INT(_security_mac_biba, OID_AUTO, destroyed_not_inited, CTLFLAG_RD,
92    &destroyed_not_inited, 0, "Count of labels destroyed but not inited");
93
94static int	trust_all_interfaces = 0;
95SYSCTL_INT(_security_mac_biba, OID_AUTO, trust_all_interfaces, CTLFLAG_RD,
96    &trust_all_interfaces, 0, "Consider all interfaces 'trusted' by MAC/Biba");
97TUNABLE_INT("security.mac.biba.trust_all_interfaces", &trust_all_interfaces);
98
99static char	trusted_interfaces[128];
100SYSCTL_STRING(_security_mac_biba, OID_AUTO, trusted_interfaces, CTLFLAG_RD,
101    trusted_interfaces, 0, "Interfaces considered 'trusted' by MAC/Biba");
102TUNABLE_STR("security.mac.biba.trusted_interfaces", trusted_interfaces,
103    sizeof(trusted_interfaces));
104
105static int	mac_biba_revocation_enabled = 0;
106SYSCTL_INT(_security_mac_biba, OID_AUTO, revocation_enabled, CTLFLAG_RW,
107    &mac_biba_revocation_enabled, 0, "Revoke access to objects on relabel");
108TUNABLE_INT("security.mac.biba.revocation_enabled",
109    &mac_biba_revocation_enabled);
110
111static int	mac_biba_slot;
112#define	SLOT(l)	((struct mac_biba *)LABEL_TO_SLOT((l), mac_biba_slot).l_ptr)
113
114MALLOC_DEFINE(M_MACBIBA, "biba label", "MAC/Biba labels");
115
116static int	mac_biba_check_vnode_open(struct ucred *cred, struct vnode *vp,
117		    struct label *vnodelabel, mode_t acc_mode);
118
119static struct mac_biba *
120biba_alloc(int how)
121{
122	struct mac_biba *mac_biba;
123
124	mac_biba = malloc(sizeof(struct mac_biba), M_MACBIBA, M_ZERO | how);
125
126	return (mac_biba);
127}
128
129static void
130biba_free(struct mac_biba *mac_biba)
131{
132
133	if (mac_biba != NULL)
134		free(mac_biba, M_MACBIBA);
135	else
136		atomic_add_int(&destroyed_not_inited, 1);
137}
138
139static int
140mac_biba_dominate_element(struct mac_biba_element *a,
141    struct mac_biba_element *b)
142{
143
144	switch(a->mbe_type) {
145	case MAC_BIBA_TYPE_EQUAL:
146	case MAC_BIBA_TYPE_HIGH:
147		return (1);
148
149	case MAC_BIBA_TYPE_LOW:
150		switch (b->mbe_type) {
151		case MAC_BIBA_TYPE_GRADE:
152		case MAC_BIBA_TYPE_HIGH:
153			return (0);
154
155		case MAC_BIBA_TYPE_EQUAL:
156		case MAC_BIBA_TYPE_LOW:
157			return (1);
158
159		default:
160			panic("mac_biba_dominate_element: b->mbe_type invalid");
161		}
162
163	case MAC_BIBA_TYPE_GRADE:
164		switch (b->mbe_type) {
165		case MAC_BIBA_TYPE_EQUAL:
166		case MAC_BIBA_TYPE_LOW:
167			return (1);
168
169		case MAC_BIBA_TYPE_HIGH:
170			return (0);
171
172		case MAC_BIBA_TYPE_GRADE:
173			return (a->mbe_grade >= b->mbe_grade);
174
175		default:
176			panic("mac_biba_dominate_element: b->mbe_type invalid");
177		}
178
179	default:
180		panic("mac_biba_dominate_element: a->mbe_type invalid");
181	}
182
183	return (0);
184}
185
186static int
187mac_biba_range_in_range(struct mac_biba *rangea, struct mac_biba *rangeb)
188{
189
190	return (mac_biba_dominate_element(&rangeb->mb_rangehigh,
191	    &rangea->mb_rangehigh) &&
192	    mac_biba_dominate_element(&rangea->mb_rangelow,
193	    &rangeb->mb_rangelow));
194}
195
196static int
197mac_biba_single_in_range(struct mac_biba *single, struct mac_biba *range)
198{
199
200	KASSERT((single->mb_flags & MAC_BIBA_FLAG_SINGLE) != 0,
201	    ("mac_biba_single_in_range: a not single"));
202	KASSERT((range->mb_flags & MAC_BIBA_FLAG_RANGE) != 0,
203	    ("mac_biba_single_in_range: b not range"));
204
205	return (mac_biba_dominate_element(&range->mb_rangehigh,
206	    &single->mb_single) &&
207	    mac_biba_dominate_element(&single->mb_single,
208	    &range->mb_rangelow));
209
210	return (1);
211}
212
213static int
214mac_biba_dominate_single(struct mac_biba *a, struct mac_biba *b)
215{
216	KASSERT((a->mb_flags & MAC_BIBA_FLAG_SINGLE) != 0,
217	    ("mac_biba_dominate_single: a not single"));
218	KASSERT((b->mb_flags & MAC_BIBA_FLAG_SINGLE) != 0,
219	    ("mac_biba_dominate_single: b not single"));
220
221	return (mac_biba_dominate_element(&a->mb_single, &b->mb_single));
222}
223
224static int
225mac_biba_equal_element(struct mac_biba_element *a, struct mac_biba_element *b)
226{
227
228	if (a->mbe_type == MAC_BIBA_TYPE_EQUAL ||
229	    b->mbe_type == MAC_BIBA_TYPE_EQUAL)
230		return (1);
231
232	return (a->mbe_type == b->mbe_type && a->mbe_grade == b->mbe_grade);
233}
234
235static int
236mac_biba_equal_range(struct mac_biba *a, struct mac_biba *b)
237{
238
239	KASSERT((a->mb_flags & MAC_BIBA_FLAG_RANGE) != 0,
240	    ("mac_biba_equal_range: a not range"));
241	KASSERT((b->mb_flags & MAC_BIBA_FLAG_RANGE) != 0,
242	    ("mac_biba_equal_range: b not range"));
243
244	return (mac_biba_equal_element(&a->mb_rangelow, &b->mb_rangelow) &&
245	    mac_biba_equal_element(&a->mb_rangehigh, &b->mb_rangehigh));
246}
247
248static int
249mac_biba_equal_single(struct mac_biba *a, struct mac_biba *b)
250{
251
252	KASSERT((a->mb_flags & MAC_BIBA_FLAG_SINGLE) != 0,
253	    ("mac_biba_equal_single: a not single"));
254	KASSERT((b->mb_flags & MAC_BIBA_FLAG_SINGLE) != 0,
255	    ("mac_biba_equal_single: b not single"));
256
257	return (mac_biba_equal_element(&a->mb_single, &b->mb_single));
258}
259
260static int
261mac_biba_high_single(struct mac_biba *mac_biba)
262{
263
264	return (mac_biba->mb_single.mbe_type == MAC_BIBA_TYPE_HIGH);
265}
266
267static int
268mac_biba_valid(struct mac_biba *mac_biba)
269{
270
271	if (mac_biba->mb_flags & MAC_BIBA_FLAG_SINGLE) {
272		switch (mac_biba->mb_single.mbe_type) {
273		case MAC_BIBA_TYPE_GRADE:
274			break;
275
276		case MAC_BIBA_TYPE_EQUAL:
277		case MAC_BIBA_TYPE_HIGH:
278		case MAC_BIBA_TYPE_LOW:
279			if (mac_biba->mb_single.mbe_grade != 0)
280				return (EINVAL);
281			break;
282
283		default:
284			return (EINVAL);
285		}
286	} else {
287		if (mac_biba->mb_single.mbe_type != MAC_BIBA_TYPE_UNDEF)
288			return (EINVAL);
289	}
290
291	if (mac_biba->mb_flags & MAC_BIBA_FLAG_RANGE) {
292		switch (mac_biba->mb_rangelow.mbe_type) {
293		case MAC_BIBA_TYPE_GRADE:
294			break;
295
296		case MAC_BIBA_TYPE_EQUAL:
297		case MAC_BIBA_TYPE_HIGH:
298		case MAC_BIBA_TYPE_LOW:
299			if (mac_biba->mb_rangelow.mbe_grade != 0)
300				return (EINVAL);
301			break;
302
303		default:
304			return (EINVAL);
305		}
306
307		switch (mac_biba->mb_rangehigh.mbe_type) {
308		case MAC_BIBA_TYPE_GRADE:
309			break;
310
311		case MAC_BIBA_TYPE_EQUAL:
312		case MAC_BIBA_TYPE_HIGH:
313		case MAC_BIBA_TYPE_LOW:
314			if (mac_biba->mb_rangehigh.mbe_grade != 0)
315				return (EINVAL);
316			break;
317
318		default:
319			return (EINVAL);
320		}
321		if (!mac_biba_dominate_element(&mac_biba->mb_rangehigh,
322		    &mac_biba->mb_rangelow))
323			return (EINVAL);
324	} else {
325		if (mac_biba->mb_rangelow.mbe_type != MAC_BIBA_TYPE_UNDEF ||
326		    mac_biba->mb_rangehigh.mbe_type != MAC_BIBA_TYPE_UNDEF)
327			return (EINVAL);
328	}
329
330	return (0);
331}
332
333static void
334mac_biba_set_range(struct mac_biba *mac_biba, u_short typelow,
335    u_short gradelow, u_short typehigh, u_short gradehigh)
336{
337
338	mac_biba->mb_rangelow.mbe_type = typelow;
339	mac_biba->mb_rangelow.mbe_grade = gradelow;
340	mac_biba->mb_rangehigh.mbe_type = typehigh;
341	mac_biba->mb_rangehigh.mbe_grade = gradehigh;
342	mac_biba->mb_flags |= MAC_BIBA_FLAG_RANGE;
343}
344
345static void
346mac_biba_set_single(struct mac_biba *mac_biba, u_short type, u_short grade)
347{
348
349	mac_biba->mb_single.mbe_type = type;
350	mac_biba->mb_single.mbe_grade = grade;
351	mac_biba->mb_flags |= MAC_BIBA_FLAG_SINGLE;
352}
353
354static void
355mac_biba_copy_range(struct mac_biba *labelfrom, struct mac_biba *labelto)
356{
357	KASSERT((labelfrom->mb_flags & MAC_BIBA_FLAG_RANGE) != 0,
358	    ("mac_biba_copy_range: labelfrom not range"));
359
360	labelto->mb_rangelow = labelfrom->mb_rangelow;
361	labelto->mb_rangehigh = labelfrom->mb_rangehigh;
362	labelto->mb_flags |= MAC_BIBA_FLAG_RANGE;
363}
364
365static void
366mac_biba_copy_single(struct mac_biba *labelfrom, struct mac_biba *labelto)
367{
368
369	KASSERT((labelfrom->mb_flags & MAC_BIBA_FLAG_SINGLE) != 0,
370	    ("mac_biba_copy_single: labelfrom not single"));
371
372	labelto->mb_single = labelfrom->mb_single;
373	labelto->mb_flags |= MAC_BIBA_FLAG_SINGLE;
374}
375
376static void
377mac_biba_copy_single_to_range(struct mac_biba *labelfrom,
378    struct mac_biba *labelto)
379{
380
381	KASSERT((labelfrom->mb_flags & MAC_BIBA_FLAG_SINGLE) != 0,
382	    ("mac_biba_copy_single_to_range: labelfrom not single"));
383
384	labelto->mb_rangelow = labelfrom->mb_single;
385	labelto->mb_rangehigh = labelfrom->mb_single;
386	labelto->mb_flags |= MAC_BIBA_FLAG_RANGE;
387}
388
389/*
390 * Policy module operations.
391 */
392static void
393mac_biba_destroy(struct mac_policy_conf *conf)
394{
395
396}
397
398static void
399mac_biba_init(struct mac_policy_conf *conf)
400{
401
402}
403
404/*
405 * Label operations.
406 */
407static void
408mac_biba_init_bpfdesc(struct bpf_d *bpf_d, struct label *label)
409{
410
411	SLOT(label) = biba_alloc(M_WAITOK);
412}
413
414static void
415mac_biba_init_cred(struct ucred *ucred, struct label *label)
416{
417
418	SLOT(label) = biba_alloc(M_WAITOK);
419}
420
421static void
422mac_biba_init_devfsdirent(struct devfs_dirent *devfs_dirent,
423    struct label *label)
424{
425
426	SLOT(label) = biba_alloc(M_WAITOK);
427}
428
429static void
430mac_biba_init_ifnet(struct ifnet *ifnet, struct label *label)
431{
432
433	SLOT(label) = biba_alloc(M_WAITOK);
434}
435
436static void
437mac_biba_init_ipq(struct ipq *ipq, struct label *label)
438{
439
440	SLOT(label) = biba_alloc(M_WAITOK);
441}
442
443static int
444mac_biba_init_mbuf(struct mbuf *mbuf, int how, struct label *label)
445{
446
447	SLOT(label) = biba_alloc(how);
448	if (SLOT(label) == NULL)
449		return (ENOMEM);
450
451	return (0);
452}
453
454static void
455mac_biba_init_mount(struct mount *mount, struct label *mntlabel,
456    struct label *fslabel)
457{
458
459	SLOT(mntlabel) = biba_alloc(M_WAITOK);
460	SLOT(fslabel) = biba_alloc(M_WAITOK);
461}
462
463static void
464mac_biba_init_socket(struct socket *socket, struct label *label,
465    struct label *peerlabel)
466{
467
468	SLOT(label) = biba_alloc(M_WAITOK);
469	SLOT(peerlabel) = biba_alloc(M_WAITOK);
470}
471
472static void
473mac_biba_init_pipe(struct pipe *pipe, struct label *label)
474{
475
476	SLOT(label) = biba_alloc(M_WAITOK);
477}
478
479static void
480mac_biba_init_temp(struct label *label)
481{
482
483	SLOT(label) = biba_alloc(M_WAITOK);
484}
485
486static void
487mac_biba_init_vnode(struct vnode *vp, struct label *label)
488{
489
490	SLOT(label) = biba_alloc(M_WAITOK);
491}
492
493static void
494mac_biba_destroy_bpfdesc(struct bpf_d *bpf_d, struct label *label)
495{
496
497	biba_free(SLOT(label));
498	SLOT(label) = NULL;
499}
500
501static void
502mac_biba_destroy_cred(struct ucred *ucred, struct label *label)
503{
504
505	biba_free(SLOT(label));
506	SLOT(label) = NULL;
507}
508
509static void
510mac_biba_destroy_devfsdirent(struct devfs_dirent *devfs_dirent,
511    struct label *label)
512{
513
514	biba_free(SLOT(label));
515	SLOT(label) = NULL;
516}
517
518static void
519mac_biba_destroy_ifnet(struct ifnet *ifnet, struct label *label)
520{
521
522	biba_free(SLOT(label));
523	SLOT(label) = NULL;
524}
525
526static void
527mac_biba_destroy_ipq(struct ipq *ipq, struct label *label)
528{
529
530	biba_free(SLOT(label));
531	SLOT(label) = NULL;
532}
533
534static void
535mac_biba_destroy_mbuf(struct mbuf *mbuf, struct label *label)
536{
537
538	biba_free(SLOT(label));
539	SLOT(label) = NULL;
540}
541
542static void
543mac_biba_destroy_mount(struct mount *mount, struct label *mntlabel,
544    struct label *fslabel)
545{
546
547	biba_free(SLOT(mntlabel));
548	SLOT(mntlabel) = NULL;
549	biba_free(SLOT(fslabel));
550	SLOT(fslabel) = NULL;
551}
552
553static void
554mac_biba_destroy_socket(struct socket *socket, struct label *label,
555    struct label *peerlabel)
556{
557
558	biba_free(SLOT(label));
559	SLOT(label) = NULL;
560	biba_free(SLOT(peerlabel));
561	SLOT(peerlabel) = NULL;
562}
563
564static void
565mac_biba_destroy_pipe(struct pipe *pipe, struct label *label)
566{
567
568	biba_free(SLOT(label));
569	SLOT(label) = NULL;
570}
571
572static void
573mac_biba_destroy_temp(struct label *label)
574{
575
576	biba_free(SLOT(label));
577	SLOT(label) = NULL;
578}
579
580static void
581mac_biba_destroy_vnode(struct vnode *vp, struct label *label)
582{
583
584	biba_free(SLOT(label));
585	SLOT(label) = NULL;
586}
587
588static int
589mac_biba_externalize(struct label *label, struct mac *extmac)
590{
591	struct mac_biba *mac_biba;
592
593	mac_biba = SLOT(label);
594
595	if (mac_biba == NULL) {
596		printf("mac_biba_externalize: NULL pointer\n");
597		return (0);
598	}
599
600	extmac->m_biba = *mac_biba;
601
602	return (0);
603}
604
605static int
606mac_biba_internalize(struct label *label, struct mac *extmac)
607{
608	struct mac_biba *mac_biba;
609	int error;
610
611	mac_biba = SLOT(label);
612
613	error = mac_biba_valid(mac_biba);
614	if (error)
615		return (error);
616
617	*mac_biba = extmac->m_biba;
618
619	return (0);
620}
621
622/*
623 * Labeling event operations: file system objects, and things that look
624 * a lot like file system objects.
625 */
626static void
627mac_biba_create_devfs_device(dev_t dev, struct devfs_dirent *devfs_dirent,
628    struct label *label)
629{
630	struct mac_biba *mac_biba;
631	int biba_type;
632
633	mac_biba = SLOT(label);
634	if (strcmp(dev->si_name, "null") == 0 ||
635	    strcmp(dev->si_name, "zero") == 0 ||
636	    strcmp(dev->si_name, "random") == 0 ||
637	    strncmp(dev->si_name, "fd/", strlen("fd/")) == 0)
638		biba_type = MAC_BIBA_TYPE_EQUAL;
639	else
640		biba_type = MAC_BIBA_TYPE_HIGH;
641	mac_biba_set_single(mac_biba, biba_type, 0);
642}
643
644static void
645mac_biba_create_devfs_directory(char *dirname, int dirnamelen,
646    struct devfs_dirent *devfs_dirent, struct label *label)
647{
648	struct mac_biba *mac_biba;
649
650	mac_biba = SLOT(label);
651	mac_biba_set_single(mac_biba, MAC_BIBA_TYPE_HIGH, 0);
652}
653
654static void
655mac_biba_create_devfs_vnode(struct devfs_dirent *devfs_dirent,
656    struct label *direntlabel, struct vnode *vp, struct label *vnodelabel)
657{
658	struct mac_biba *source, *dest;
659
660	source = SLOT(direntlabel);
661	dest = SLOT(vnodelabel);
662	mac_biba_copy_single(source, dest);
663}
664
665static void
666mac_biba_create_vnode(struct ucred *cred, struct vnode *parent,
667    struct label *parentlabel, struct vnode *child, struct label *childlabel)
668{
669	struct mac_biba *source, *dest;
670
671	source = SLOT(&cred->cr_label);
672	dest = SLOT(childlabel);
673
674	mac_biba_copy_single(source, dest);
675}
676
677static void
678mac_biba_create_mount(struct ucred *cred, struct mount *mp,
679    struct label *mntlabel, struct label *fslabel)
680{
681	struct mac_biba *source, *dest;
682
683	source = SLOT(&cred->cr_label);
684	dest = SLOT(mntlabel);
685	mac_biba_copy_single(source, dest);
686	dest = SLOT(fslabel);
687	mac_biba_copy_single(source, dest);
688}
689
690static void
691mac_biba_create_root_mount(struct ucred *cred, struct mount *mp,
692    struct label *mntlabel, struct label *fslabel)
693{
694	struct mac_biba *mac_biba;
695
696	/* Always mount root as high integrity. */
697	mac_biba = SLOT(fslabel);
698	mac_biba_set_single(mac_biba, MAC_BIBA_TYPE_HIGH, 0);
699	mac_biba = SLOT(mntlabel);
700	mac_biba_set_single(mac_biba, MAC_BIBA_TYPE_HIGH, 0);
701}
702
703static void
704mac_biba_relabel_vnode(struct ucred *cred, struct vnode *vp,
705    struct label *vnodelabel, struct label *label)
706{
707	struct mac_biba *source, *dest;
708
709	source = SLOT(label);
710	dest = SLOT(vnodelabel);
711
712	mac_biba_copy_single(source, dest);
713}
714
715static void
716mac_biba_update_devfsdirent(struct devfs_dirent *devfs_dirent,
717    struct label *direntlabel, struct vnode *vp, struct label *vnodelabel)
718{
719	struct mac_biba *source, *dest;
720
721	source = SLOT(vnodelabel);
722	dest = SLOT(direntlabel);
723
724	mac_biba_copy_single(source, dest);
725}
726
727static void
728mac_biba_update_procfsvnode(struct vnode *vp, struct label *vnodelabel,
729    struct ucred *cred)
730{
731	struct mac_biba *source, *dest;
732
733	source = SLOT(&cred->cr_label);
734	dest = SLOT(vnodelabel);
735
736	/*
737	 * Only copy the single, not the range, since vnodes only have
738	 * a single.
739	 */
740	mac_biba_copy_single(source, dest);
741}
742
743static int
744mac_biba_update_vnode_from_externalized(struct vnode *vp,
745    struct label *vnodelabel, struct mac *extmac)
746{
747	struct mac_biba *source, *dest;
748	int error;
749
750	source = &extmac->m_biba;
751	dest = SLOT(vnodelabel);
752
753	error = mac_biba_valid(source);
754	if (error)
755		return (error);
756
757	if ((source->mb_flags & MAC_BIBA_FLAGS_BOTH) != MAC_BIBA_FLAG_SINGLE)
758		return (EINVAL);
759
760	mac_biba_copy_single(source, dest);
761
762	return (0);
763}
764
765static void
766mac_biba_update_vnode_from_mount(struct vnode *vp, struct label *vnodelabel,
767    struct mount *mp, struct label *fslabel)
768{
769	struct mac_biba *source, *dest;
770
771	source = SLOT(fslabel);
772	dest = SLOT(vnodelabel);
773
774	mac_biba_copy_single(source, dest);
775}
776
777/*
778 * Labeling event operations: IPC object.
779 */
780static void
781mac_biba_create_mbuf_from_socket(struct socket *so, struct label *socketlabel,
782    struct mbuf *m, struct label *mbuflabel)
783{
784	struct mac_biba *source, *dest;
785
786	source = SLOT(socketlabel);
787	dest = SLOT(mbuflabel);
788
789	mac_biba_copy_single(source, dest);
790}
791
792static void
793mac_biba_create_socket(struct ucred *cred, struct socket *socket,
794    struct label *socketlabel)
795{
796	struct mac_biba *source, *dest;
797
798	source = SLOT(&cred->cr_label);
799	dest = SLOT(socketlabel);
800
801	mac_biba_copy_single(source, dest);
802	mac_biba_copy_single_to_range(source, dest);
803}
804
805static void
806mac_biba_create_pipe(struct ucred *cred, struct pipe *pipe,
807    struct label *pipelabel)
808{
809	struct mac_biba *source, *dest;
810
811	source = SLOT(&cred->cr_label);
812	dest = SLOT(pipelabel);
813
814	mac_biba_copy_single(source, dest);
815}
816
817static void
818mac_biba_create_socket_from_socket(struct socket *oldsocket,
819    struct label *oldsocketlabel, struct socket *newsocket,
820    struct label *newsocketlabel)
821{
822	struct mac_biba *source, *dest;
823
824	source = SLOT(oldsocketlabel);
825	dest = SLOT(newsocketlabel);
826
827	mac_biba_copy_single(source, dest);
828	mac_biba_copy_range(source, dest);
829}
830
831static void
832mac_biba_relabel_socket(struct ucred *cred, struct socket *socket,
833    struct label *socketlabel, struct label *newlabel)
834{
835	struct mac_biba *source, *dest;
836
837	source = SLOT(newlabel);
838	dest = SLOT(socketlabel);
839
840	mac_biba_copy_single(source, dest);
841	mac_biba_copy_range(source, dest);
842}
843
844static void
845mac_biba_relabel_pipe(struct ucred *cred, struct pipe *pipe,
846    struct label *pipelabel, struct label *newlabel)
847{
848	struct mac_biba *source, *dest;
849
850	source = SLOT(newlabel);
851	dest = SLOT(pipelabel);
852
853	mac_biba_copy_single(source, dest);
854}
855
856static void
857mac_biba_set_socket_peer_from_mbuf(struct mbuf *mbuf, struct label *mbuflabel,
858    struct socket *socket, struct label *socketpeerlabel)
859{
860	struct mac_biba *source, *dest;
861
862	source = SLOT(mbuflabel);
863	dest = SLOT(socketpeerlabel);
864
865	mac_biba_copy_single(source, dest);
866}
867
868/*
869 * Labeling event operations: network objects.
870 */
871static void
872mac_biba_set_socket_peer_from_socket(struct socket *oldsocket,
873    struct label *oldsocketlabel, struct socket *newsocket,
874    struct label *newsocketpeerlabel)
875{
876	struct mac_biba *source, *dest;
877
878	source = SLOT(oldsocketlabel);
879	dest = SLOT(newsocketpeerlabel);
880
881	mac_biba_copy_single(source, dest);
882}
883
884static void
885mac_biba_create_bpfdesc(struct ucred *cred, struct bpf_d *bpf_d,
886    struct label *bpflabel)
887{
888	struct mac_biba *source, *dest;
889
890	source = SLOT(&cred->cr_label);
891	dest = SLOT(bpflabel);
892
893	mac_biba_copy_single(source, dest);
894}
895
896static void
897mac_biba_create_ifnet(struct ifnet *ifnet, struct label *ifnetlabel)
898{
899	char tifname[IFNAMSIZ], ifname[IFNAMSIZ], *p, *q;
900	char tiflist[sizeof(trusted_interfaces)];
901	struct mac_biba *dest;
902	int len, grade;
903
904	dest = SLOT(ifnetlabel);
905
906	if (ifnet->if_type == IFT_LOOP) {
907		grade = MAC_BIBA_TYPE_EQUAL;
908		goto set;
909	}
910
911	if (trust_all_interfaces) {
912		grade = MAC_BIBA_TYPE_HIGH;
913		goto set;
914	}
915
916	grade = MAC_BIBA_TYPE_LOW;
917
918	if (trusted_interfaces[0] == '\0' ||
919	    !strvalid(trusted_interfaces, sizeof(trusted_interfaces)))
920		goto set;
921
922	for (p = trusted_interfaces, q = tiflist; *p != '\0'; p++, q++)
923		if(*p != ' ' && *p != '\t')
924			*q = *p;
925
926	snprintf(ifname, IFNAMSIZ, "%s%d", ifnet->if_name, ifnet->if_unit);
927
928	for (p = q = tiflist;; p++) {
929		if (*p == ',' || *p == '\0') {
930			len = p - q;
931			if (len < IFNAMSIZ) {
932				bzero(tifname, sizeof(tifname));
933				bcopy(q, tifname, len);
934				if (strcmp(tifname, ifname) == 0) {
935					grade = MAC_BIBA_TYPE_HIGH;
936					break;
937				}
938			}
939			if (*p == '\0')
940				break;
941			q = p + 1;
942		}
943	}
944set:
945	mac_biba_set_single(dest, grade, 0);
946	mac_biba_set_range(dest, grade, 0, grade, 0);
947}
948
949static void
950mac_biba_create_ipq(struct mbuf *fragment, struct label *fragmentlabel,
951    struct ipq *ipq, struct label *ipqlabel)
952{
953	struct mac_biba *source, *dest;
954
955	source = SLOT(fragmentlabel);
956	dest = SLOT(ipqlabel);
957
958	mac_biba_copy_single(source, dest);
959}
960
961static void
962mac_biba_create_datagram_from_ipq(struct ipq *ipq, struct label *ipqlabel,
963    struct mbuf *datagram, struct label *datagramlabel)
964{
965	struct mac_biba *source, *dest;
966
967	source = SLOT(ipqlabel);
968	dest = SLOT(datagramlabel);
969
970	/* Just use the head, since we require them all to match. */
971	mac_biba_copy_single(source, dest);
972}
973
974static void
975mac_biba_create_fragment(struct mbuf *datagram, struct label *datagramlabel,
976    struct mbuf *fragment, struct label *fragmentlabel)
977{
978	struct mac_biba *source, *dest;
979
980	source = SLOT(datagramlabel);
981	dest = SLOT(fragmentlabel);
982
983	mac_biba_copy_single(source, dest);
984}
985
986static void
987mac_biba_create_mbuf_from_mbuf(struct mbuf *oldmbuf,
988    struct label *oldmbuflabel, struct mbuf *newmbuf,
989    struct label *newmbuflabel)
990{
991	struct mac_biba *source, *dest;
992
993	source = SLOT(oldmbuflabel);
994	dest = SLOT(newmbuflabel);
995
996	mac_biba_copy_single(source, dest);
997}
998
999static void
1000mac_biba_create_mbuf_linklayer(struct ifnet *ifnet, struct label *ifnetlabel,
1001    struct mbuf *mbuf, struct label *mbuflabel)
1002{
1003	struct mac_biba *dest;
1004
1005	dest = SLOT(mbuflabel);
1006
1007	mac_biba_set_single(dest, MAC_BIBA_TYPE_EQUAL, 0);
1008}
1009
1010static void
1011mac_biba_create_mbuf_from_bpfdesc(struct bpf_d *bpf_d, struct label *bpflabel,
1012    struct mbuf *mbuf, struct label *mbuflabel)
1013{
1014	struct mac_biba *source, *dest;
1015
1016	source = SLOT(bpflabel);
1017	dest = SLOT(mbuflabel);
1018
1019	mac_biba_copy_single(source, dest);
1020}
1021
1022static void
1023mac_biba_create_mbuf_from_ifnet(struct ifnet *ifnet, struct label *ifnetlabel,
1024    struct mbuf *m, struct label *mbuflabel)
1025{
1026	struct mac_biba *source, *dest;
1027
1028	source = SLOT(ifnetlabel);
1029	dest = SLOT(mbuflabel);
1030
1031	mac_biba_copy_single(source, dest);
1032}
1033
1034static void
1035mac_biba_create_mbuf_multicast_encap(struct mbuf *oldmbuf,
1036    struct label *oldmbuflabel, struct ifnet *ifnet, struct label *ifnetlabel,
1037    struct mbuf *newmbuf, struct label *newmbuflabel)
1038{
1039	struct mac_biba *source, *dest;
1040
1041	source = SLOT(oldmbuflabel);
1042	dest = SLOT(newmbuflabel);
1043
1044	mac_biba_copy_single(source, dest);
1045}
1046
1047static void
1048mac_biba_create_mbuf_netlayer(struct mbuf *oldmbuf, struct label *oldmbuflabel,
1049    struct mbuf *newmbuf, struct label *newmbuflabel)
1050{
1051	struct mac_biba *source, *dest;
1052
1053	source = SLOT(oldmbuflabel);
1054	dest = SLOT(newmbuflabel);
1055
1056	mac_biba_copy_single(source, dest);
1057}
1058
1059static int
1060mac_biba_fragment_match(struct mbuf *fragment, struct label *fragmentlabel,
1061    struct ipq *ipq, struct label *ipqlabel)
1062{
1063	struct mac_biba *a, *b;
1064
1065	a = SLOT(ipqlabel);
1066	b = SLOT(fragmentlabel);
1067
1068	return (mac_biba_equal_single(a, b));
1069}
1070
1071static void
1072mac_biba_relabel_ifnet(struct ucred *cred, struct ifnet *ifnet,
1073    struct label *ifnetlabel, struct label *newlabel)
1074{
1075	struct mac_biba *source, *dest;
1076
1077	source = SLOT(newlabel);
1078	dest = SLOT(ifnetlabel);
1079
1080	mac_biba_copy_single(source, dest);
1081	mac_biba_copy_range(source, dest);
1082}
1083
1084static void
1085mac_biba_update_ipq(struct mbuf *fragment, struct label *fragmentlabel,
1086    struct ipq *ipq, struct label *ipqlabel)
1087{
1088
1089	/* NOOP: we only accept matching labels, so no need to update */
1090}
1091
1092/*
1093 * Labeling event operations: processes.
1094 */
1095static void
1096mac_biba_create_cred(struct ucred *cred_parent, struct ucred *cred_child)
1097{
1098	struct mac_biba *source, *dest;
1099
1100	source = SLOT(&cred_parent->cr_label);
1101	dest = SLOT(&cred_child->cr_label);
1102
1103	mac_biba_copy_single(source, dest);
1104	mac_biba_copy_range(source, dest);
1105}
1106
1107static void
1108mac_biba_execve_transition(struct ucred *old, struct ucred *new,
1109    struct vnode *vp, struct mac *vnodelabel)
1110{
1111	struct mac_biba *source, *dest;
1112
1113	source = SLOT(&old->cr_label);
1114	dest = SLOT(&new->cr_label);
1115
1116	mac_biba_copy_single(source, dest);
1117	mac_biba_copy_range(source, dest);
1118}
1119
1120static int
1121mac_biba_execve_will_transition(struct ucred *old, struct vnode *vp,
1122    struct mac *vnodelabel)
1123{
1124
1125	return (0);
1126}
1127
1128static void
1129mac_biba_create_proc0(struct ucred *cred)
1130{
1131	struct mac_biba *dest;
1132
1133	dest = SLOT(&cred->cr_label);
1134
1135	mac_biba_set_single(dest, MAC_BIBA_TYPE_EQUAL, 0);
1136	mac_biba_set_range(dest, MAC_BIBA_TYPE_LOW, 0, MAC_BIBA_TYPE_HIGH, 0);
1137}
1138
1139static void
1140mac_biba_create_proc1(struct ucred *cred)
1141{
1142	struct mac_biba *dest;
1143
1144	dest = SLOT(&cred->cr_label);
1145
1146	mac_biba_set_single(dest, MAC_BIBA_TYPE_HIGH, 0);
1147	mac_biba_set_range(dest, MAC_BIBA_TYPE_LOW, 0, MAC_BIBA_TYPE_HIGH, 0);
1148}
1149
1150static void
1151mac_biba_relabel_cred(struct ucred *cred, struct label *newlabel)
1152{
1153	struct mac_biba *source, *dest;
1154
1155	source = SLOT(newlabel);
1156	dest = SLOT(&cred->cr_label);
1157
1158	mac_biba_copy_single(source, dest);
1159	mac_biba_copy_range(source, dest);
1160}
1161
1162/*
1163 * Access control checks.
1164 */
1165static int
1166mac_biba_check_bpfdesc_receive(struct bpf_d *bpf_d, struct label *bpflabel,
1167    struct ifnet *ifnet, struct label *ifnetlabel)
1168{
1169	struct mac_biba *a, *b;
1170
1171	if (!mac_biba_enabled)
1172		return (0);
1173
1174	a = SLOT(bpflabel);
1175	b = SLOT(ifnetlabel);
1176
1177	if (mac_biba_equal_single(a, b))
1178		return (0);
1179	return (EACCES);
1180}
1181
1182static int
1183mac_biba_check_cred_relabel(struct ucred *cred, struct label *newlabel)
1184{
1185	struct mac_biba *subj, *new;
1186
1187	subj = SLOT(&cred->cr_label);
1188	new = SLOT(newlabel);
1189
1190	if ((new->mb_flags & MAC_BIBA_FLAGS_BOTH) != MAC_BIBA_FLAGS_BOTH)
1191		return (EINVAL);
1192
1193	/*
1194	 * XXX: Allow processes with root privilege to set labels outside
1195	 * their range, so suid things like "su" work.  This WILL go away
1196	 * when we figure out the 'correct' solution...
1197	 */
1198	if (!suser_cred(cred, 0))
1199		return (0);
1200
1201	/*
1202	 * The new single must be in the old range.
1203	 */
1204	if (!mac_biba_single_in_range(new, subj))
1205		return (EPERM);
1206
1207	/*
1208	 * The new range must be in the old range.
1209	 */
1210	if (!mac_biba_range_in_range(new, subj))
1211		return (EPERM);
1212
1213	/*
1214	 * XXX: Don't permit EQUAL in a label unless the subject has EQUAL.
1215	 */
1216
1217	return (0);
1218}
1219
1220static int
1221mac_biba_check_cred_visible(struct ucred *u1, struct ucred *u2)
1222{
1223	struct mac_biba *subj, *obj;
1224
1225	if (!mac_biba_enabled)
1226		return (0);
1227
1228	subj = SLOT(&u1->cr_label);
1229	obj = SLOT(&u2->cr_label);
1230
1231	/* XXX: range */
1232	if (!mac_biba_dominate_single(obj, subj))
1233		return (ESRCH);
1234
1235	return (0);
1236}
1237
1238static int
1239mac_biba_check_ifnet_relabel(struct ucred *cred, struct ifnet *ifnet,
1240    struct label *ifnetlabel, struct label *newlabel)
1241{
1242	struct mac_biba *subj, *new;
1243
1244	subj = SLOT(&cred->cr_label);
1245	new = SLOT(newlabel);
1246
1247	if ((new->mb_flags & MAC_BIBA_FLAGS_BOTH) != MAC_BIBA_FLAGS_BOTH)
1248		return (EINVAL);
1249
1250	/*
1251	 * XXX: Only Biba HIGH subjects may relabel interfaces. */
1252	if (!mac_biba_high_single(subj))
1253		return (EPERM);
1254
1255	return (suser_cred(cred, 0));
1256}
1257
1258static int
1259mac_biba_check_ifnet_transmit(struct ifnet *ifnet, struct label *ifnetlabel,
1260    struct mbuf *m, struct label *mbuflabel)
1261{
1262	struct mac_biba *p, *i;
1263
1264	if (!mac_biba_enabled)
1265		return (0);
1266
1267	p = SLOT(mbuflabel);
1268	i = SLOT(ifnetlabel);
1269
1270	return (mac_biba_single_in_range(p, i) ? 0 : EACCES);
1271}
1272
1273static int
1274mac_biba_check_mount_stat(struct ucred *cred, struct mount *mp,
1275    struct label *mntlabel)
1276{
1277	struct mac_biba *subj, *obj;
1278
1279	if (!mac_biba_enabled)
1280		return (0);
1281
1282	subj = SLOT(&cred->cr_label);
1283	obj = SLOT(mntlabel);
1284
1285	if (!mac_biba_dominate_single(obj, subj))
1286		return (EACCES);
1287
1288	return (0);
1289}
1290
1291static int
1292mac_biba_check_pipe_ioctl(struct ucred *cred, struct pipe *pipe,
1293    struct label *pipelabel, unsigned long cmd, void /* caddr_t */ *data)
1294{
1295
1296	if(!mac_biba_enabled)
1297		return (0);
1298
1299	/* XXX: This will be implemented soon... */
1300
1301	return (0);
1302}
1303
1304static int
1305mac_biba_check_pipe_poll(struct ucred *cred, struct pipe *pipe,
1306    struct label *pipelabel)
1307{
1308	struct mac_biba *subj, *obj;
1309
1310	if (!mac_biba_enabled)
1311		return (0);
1312
1313	subj = SLOT(&cred->cr_label);
1314	obj = SLOT((pipelabel));
1315
1316	if (!mac_biba_dominate_single(obj, subj))
1317		return (EACCES);
1318
1319	return (0);
1320}
1321
1322static int
1323mac_biba_check_pipe_read(struct ucred *cred, struct pipe *pipe,
1324    struct label *pipelabel)
1325{
1326	struct mac_biba *subj, *obj;
1327
1328	if (!mac_biba_enabled)
1329		return (0);
1330
1331	subj = SLOT(&cred->cr_label);
1332	obj = SLOT((pipelabel));
1333
1334	if (!mac_biba_dominate_single(obj, subj))
1335		return (EACCES);
1336
1337	return (0);
1338}
1339
1340static int
1341mac_biba_check_pipe_relabel(struct ucred *cred, struct pipe *pipe,
1342    struct label *pipelabel, struct label *newlabel)
1343{
1344	struct mac_biba *subj, *obj, *new;
1345
1346	new = SLOT(newlabel);
1347	subj = SLOT(&cred->cr_label);
1348	obj = SLOT(pipelabel);
1349
1350	if ((new->mb_flags & MAC_BIBA_FLAGS_BOTH) != MAC_BIBA_FLAG_SINGLE)
1351		return (EINVAL);
1352
1353	/*
1354	 * To relabel a pipe, the old pipe label must be in the subject
1355	 * range.
1356	 */
1357	if (!mac_biba_single_in_range(obj, subj))
1358		return (EPERM);
1359
1360	/*
1361	 * To relabel a pipe, the new pipe label must be in the subject
1362	 * range.
1363	 */
1364	if (!mac_biba_single_in_range(new, subj))
1365		return (EPERM);
1366
1367	/*
1368	 * XXX: Don't permit EQUAL in a label unless the subject has EQUAL.
1369	 */
1370
1371	return (0);
1372}
1373
1374static int
1375mac_biba_check_pipe_stat(struct ucred *cred, struct pipe *pipe,
1376    struct label *pipelabel)
1377{
1378	struct mac_biba *subj, *obj;
1379
1380	if (!mac_biba_enabled)
1381		return (0);
1382
1383	subj = SLOT(&cred->cr_label);
1384	obj = SLOT((pipelabel));
1385
1386	if (!mac_biba_dominate_single(obj, subj))
1387		return (EACCES);
1388
1389	return (0);
1390}
1391
1392static int
1393mac_biba_check_pipe_write(struct ucred *cred, struct pipe *pipe,
1394    struct label *pipelabel)
1395{
1396	struct mac_biba *subj, *obj;
1397
1398	if (!mac_biba_enabled)
1399		return (0);
1400
1401	subj = SLOT(&cred->cr_label);
1402	obj = SLOT((pipelabel));
1403
1404	if (!mac_biba_dominate_single(subj, obj))
1405		return (EACCES);
1406
1407	return (0);
1408}
1409
1410static int
1411mac_biba_check_proc_debug(struct ucred *cred, struct proc *proc)
1412{
1413	struct mac_biba *subj, *obj;
1414
1415	if (!mac_biba_enabled)
1416		return (0);
1417
1418	subj = SLOT(&cred->cr_label);
1419	obj = SLOT(&proc->p_ucred->cr_label);
1420
1421	/* XXX: range checks */
1422	if (!mac_biba_dominate_single(obj, subj))
1423		return (ESRCH);
1424	if (!mac_biba_dominate_single(subj, obj))
1425		return (EACCES);
1426
1427	return (0);
1428}
1429
1430static int
1431mac_biba_check_proc_sched(struct ucred *cred, struct proc *proc)
1432{
1433	struct mac_biba *subj, *obj;
1434
1435	if (!mac_biba_enabled)
1436		return (0);
1437
1438	subj = SLOT(&cred->cr_label);
1439	obj = SLOT(&proc->p_ucred->cr_label);
1440
1441	/* XXX: range checks */
1442	if (!mac_biba_dominate_single(obj, subj))
1443		return (ESRCH);
1444	if (!mac_biba_dominate_single(subj, obj))
1445		return (EACCES);
1446
1447	return (0);
1448}
1449
1450static int
1451mac_biba_check_proc_signal(struct ucred *cred, struct proc *proc, int signum)
1452{
1453	struct mac_biba *subj, *obj;
1454
1455	if (!mac_biba_enabled)
1456		return (0);
1457
1458	subj = SLOT(&cred->cr_label);
1459	obj = SLOT(&proc->p_ucred->cr_label);
1460
1461	/* XXX: range checks */
1462	if (!mac_biba_dominate_single(obj, subj))
1463		return (ESRCH);
1464	if (!mac_biba_dominate_single(subj, obj))
1465		return (EACCES);
1466
1467	return (0);
1468}
1469
1470static int
1471mac_biba_check_socket_deliver(struct socket *so, struct label *socketlabel,
1472    struct mbuf *m, struct label *mbuflabel)
1473{
1474	struct mac_biba *p, *s;
1475
1476	if (!mac_biba_enabled)
1477		return (0);
1478
1479	p = SLOT(mbuflabel);
1480	s = SLOT(socketlabel);
1481
1482	return (mac_biba_equal_single(p, s) ? 0 : EACCES);
1483}
1484
1485static int
1486mac_biba_check_socket_relabel(struct ucred *cred, struct socket *socket,
1487    struct label *socketlabel, struct label *newlabel)
1488{
1489	struct mac_biba *subj, *obj, *new;
1490
1491	new = SLOT(newlabel);
1492	subj = SLOT(&cred->cr_label);
1493	obj = SLOT(socketlabel);
1494
1495	if ((new->mb_flags & MAC_BIBA_FLAGS_BOTH) != MAC_BIBA_FLAG_SINGLE)
1496		return (EINVAL);
1497
1498	/*
1499	 * To relabel a socket, the old socket label must be in the subject
1500	 * range.
1501	 */
1502	if (!mac_biba_single_in_range(obj, subj))
1503		return (EPERM);
1504
1505	/*
1506	 * To relabel a socket, the new socket label must be in the subject
1507	 * range.
1508	 */
1509	if (!mac_biba_single_in_range(new, subj))
1510		return (EPERM);
1511
1512	/*
1513	 * XXX: Don't permit EQUAL in a label unless the subject has EQUAL.
1514	 */
1515
1516	return (0);
1517}
1518
1519static int
1520mac_biba_check_socket_visible(struct ucred *cred, struct socket *socket,
1521    struct label *socketlabel)
1522{
1523	struct mac_biba *subj, *obj;
1524
1525	subj = SLOT(&cred->cr_label);
1526	obj = SLOT(socketlabel);
1527
1528	if (!mac_biba_dominate_single(obj, subj))
1529		return (ENOENT);
1530
1531	return (0);
1532}
1533
1534static int
1535mac_biba_check_vnode_access(struct ucred *cred, struct vnode *vp,
1536    struct label *label, mode_t flags)
1537{
1538
1539	return (mac_biba_check_vnode_open(cred, vp, label, flags));
1540}
1541
1542static int
1543mac_biba_check_vnode_chdir(struct ucred *cred, struct vnode *dvp,
1544    struct label *dlabel)
1545{
1546	struct mac_biba *subj, *obj;
1547
1548	if (!mac_biba_enabled)
1549		return (0);
1550
1551	subj = SLOT(&cred->cr_label);
1552	obj = SLOT(dlabel);
1553
1554	if (!mac_biba_dominate_single(obj, subj))
1555		return (EACCES);
1556
1557	return (0);
1558}
1559
1560static int
1561mac_biba_check_vnode_chroot(struct ucred *cred, struct vnode *dvp,
1562    struct label *dlabel)
1563{
1564	struct mac_biba *subj, *obj;
1565
1566	if (!mac_biba_enabled)
1567		return (0);
1568
1569	subj = SLOT(&cred->cr_label);
1570	obj = SLOT(dlabel);
1571
1572	if (!mac_biba_dominate_single(obj, subj))
1573		return (EACCES);
1574
1575	return (0);
1576}
1577
1578static int
1579mac_biba_check_vnode_create(struct ucred *cred, struct vnode *dvp,
1580    struct label *dlabel, struct componentname *cnp, struct vattr *vap)
1581{
1582	struct mac_biba *subj, *obj;
1583
1584	if (!mac_biba_enabled)
1585		return (0);
1586
1587	subj = SLOT(&cred->cr_label);
1588	obj = SLOT(dlabel);
1589
1590	if (!mac_biba_dominate_single(subj, obj))
1591		return (EACCES);
1592
1593	return (0);
1594}
1595
1596static int
1597mac_biba_check_vnode_delete(struct ucred *cred, struct vnode *dvp,
1598    struct label *dlabel, struct vnode *vp, struct label *label,
1599    struct componentname *cnp)
1600{
1601	struct mac_biba *subj, *obj;
1602
1603	if (!mac_biba_enabled)
1604		return (0);
1605
1606	subj = SLOT(&cred->cr_label);
1607	obj = SLOT(dlabel);
1608
1609	if (!mac_biba_dominate_single(subj, obj))
1610		return (EACCES);
1611
1612	obj = SLOT(label);
1613
1614	if (!mac_biba_dominate_single(subj, obj))
1615		return (EACCES);
1616
1617	return (0);
1618}
1619
1620static int
1621mac_biba_check_vnode_deleteacl(struct ucred *cred, struct vnode *vp,
1622    struct label *label, acl_type_t type)
1623{
1624	struct mac_biba *subj, *obj;
1625
1626	if (!mac_biba_enabled)
1627		return (0);
1628
1629	subj = SLOT(&cred->cr_label);
1630	obj = SLOT(label);
1631
1632	if (!mac_biba_dominate_single(subj, obj))
1633		return (EACCES);
1634
1635	return (0);
1636}
1637
1638static int
1639mac_biba_check_vnode_exec(struct ucred *cred, struct vnode *vp,
1640    struct label *label)
1641{
1642	struct mac_biba *subj, *obj;
1643
1644	if (!mac_biba_enabled)
1645		return (0);
1646
1647	subj = SLOT(&cred->cr_label);
1648	obj = SLOT(label);
1649
1650	if (!mac_biba_dominate_single(obj, subj))
1651		return (EACCES);
1652
1653	return (0);
1654}
1655
1656static int
1657mac_biba_check_vnode_getacl(struct ucred *cred, struct vnode *vp,
1658    struct label *label, acl_type_t type)
1659{
1660	struct mac_biba *subj, *obj;
1661
1662	if (!mac_biba_enabled)
1663		return (0);
1664
1665	subj = SLOT(&cred->cr_label);
1666	obj = SLOT(label);
1667
1668	if (!mac_biba_dominate_single(obj, subj))
1669		return (EACCES);
1670
1671	return (0);
1672}
1673
1674static int
1675mac_biba_check_vnode_getextattr(struct ucred *cred, struct vnode *vp,
1676    struct label *label, int attrnamespace, const char *name, struct uio *uio)
1677{
1678	struct mac_biba *subj, *obj;
1679
1680	if (!mac_biba_enabled)
1681		return (0);
1682
1683	subj = SLOT(&cred->cr_label);
1684	obj = SLOT(label);
1685
1686	if (!mac_biba_dominate_single(obj, subj))
1687		return (EACCES);
1688
1689	return (0);
1690}
1691
1692static int
1693mac_biba_check_vnode_lookup(struct ucred *cred, struct vnode *dvp,
1694    struct label *dlabel, struct componentname *cnp)
1695{
1696	struct mac_biba *subj, *obj;
1697
1698	if (!mac_biba_enabled)
1699		return (0);
1700
1701	subj = SLOT(&cred->cr_label);
1702	obj = SLOT(dlabel);
1703
1704	if (!mac_biba_dominate_single(obj, subj))
1705		return (EACCES);
1706
1707	return (0);
1708}
1709
1710static int
1711mac_biba_check_vnode_open(struct ucred *cred, struct vnode *vp,
1712    struct label *vnodelabel, mode_t acc_mode)
1713{
1714	struct mac_biba *subj, *obj;
1715
1716	if (!mac_biba_enabled)
1717		return (0);
1718
1719	subj = SLOT(&cred->cr_label);
1720	obj = SLOT(vnodelabel);
1721
1722	/* XXX privilege override for admin? */
1723	if (acc_mode & (VREAD | VEXEC | VSTAT)) {
1724		if (!mac_biba_dominate_single(obj, subj))
1725			return (EACCES);
1726	}
1727	if (acc_mode & (VWRITE | VAPPEND | VADMIN)) {
1728		if (!mac_biba_dominate_single(subj, obj))
1729			return (EACCES);
1730	}
1731
1732	return (0);
1733}
1734
1735static int
1736mac_biba_check_vnode_poll(struct ucred *active_cred, struct ucred *file_cred,
1737    struct vnode *vp, struct label *label)
1738{
1739	struct mac_biba *subj, *obj;
1740
1741	if (!mac_biba_enabled || !mac_biba_revocation_enabled)
1742		return (0);
1743
1744	subj = SLOT(&active_cred->cr_label);
1745	obj = SLOT(label);
1746
1747	if (!mac_biba_dominate_single(obj, subj))
1748		return (EACCES);
1749
1750	return (0);
1751}
1752
1753static int
1754mac_biba_check_vnode_read(struct ucred *active_cred, struct ucred *file_cred,
1755    struct vnode *vp, struct label *label)
1756{
1757	struct mac_biba *subj, *obj;
1758
1759	if (!mac_biba_enabled || !mac_biba_revocation_enabled)
1760		return (0);
1761
1762	subj = SLOT(&active_cred->cr_label);
1763	obj = SLOT(label);
1764
1765	if (!mac_biba_dominate_single(obj, subj))
1766		return (EACCES);
1767
1768	return (0);
1769}
1770
1771static int
1772mac_biba_check_vnode_readdir(struct ucred *cred, struct vnode *dvp,
1773    struct label *dlabel)
1774{
1775	struct mac_biba *subj, *obj;
1776
1777	if (!mac_biba_enabled)
1778		return (0);
1779
1780	subj = SLOT(&cred->cr_label);
1781	obj = SLOT(dlabel);
1782
1783	if (!mac_biba_dominate_single(obj, subj))
1784		return (EACCES);
1785
1786	return (0);
1787}
1788
1789static int
1790mac_biba_check_vnode_readlink(struct ucred *cred, struct vnode *vp,
1791    struct label *label)
1792{
1793	struct mac_biba *subj, *obj;
1794
1795	if (!mac_biba_enabled)
1796		return (0);
1797
1798	subj = SLOT(&cred->cr_label);
1799	obj = SLOT(label);
1800
1801	if (!mac_biba_dominate_single(obj, subj))
1802		return (EACCES);
1803
1804	return (0);
1805}
1806
1807static int
1808mac_biba_check_vnode_relabel(struct ucred *cred, struct vnode *vp,
1809    struct label *vnodelabel, struct label *newlabel)
1810{
1811	struct mac_biba *old, *new, *subj;
1812
1813	old = SLOT(vnodelabel);
1814	new = SLOT(newlabel);
1815	subj = SLOT(&cred->cr_label);
1816
1817	if ((new->mb_flags & MAC_BIBA_FLAGS_BOTH) != MAC_BIBA_FLAG_SINGLE)
1818		return (EINVAL);
1819
1820	/*
1821	 * To relabel a vnode, the old vnode label must be in the subject
1822	 * range.
1823	 */
1824	if (!mac_biba_single_in_range(old, subj))
1825		return (EPERM);
1826
1827	/*
1828	 * To relabel a vnode, the new vnode label must be in the subject
1829	 * range.
1830	 */
1831	if (!mac_biba_single_in_range(new, subj))
1832		return (EPERM);
1833
1834	/*
1835	 * XXX: Don't permit EQUAL in a label unless the subject has EQUAL.
1836	 */
1837
1838	return (suser_cred(cred, 0));
1839}
1840
1841static int
1842mac_biba_check_vnode_rename_from(struct ucred *cred, struct vnode *dvp,
1843    struct label *dlabel, struct vnode *vp, struct label *label,
1844    struct componentname *cnp)
1845{
1846	struct mac_biba *subj, *obj;
1847
1848	if (!mac_biba_enabled)
1849		return (0);
1850
1851	subj = SLOT(&cred->cr_label);
1852	obj = SLOT(dlabel);
1853
1854	if (!mac_biba_dominate_single(subj, obj))
1855		return (EACCES);
1856
1857	obj = SLOT(label);
1858
1859	if (!mac_biba_dominate_single(subj, obj))
1860		return (EACCES);
1861
1862	return (0);
1863}
1864
1865static int
1866mac_biba_check_vnode_rename_to(struct ucred *cred, struct vnode *dvp,
1867    struct label *dlabel, struct vnode *vp, struct label *label, int samedir,
1868    struct componentname *cnp)
1869{
1870	struct mac_biba *subj, *obj;
1871
1872	if (!mac_biba_enabled)
1873		return (0);
1874
1875	subj = SLOT(&cred->cr_label);
1876	obj = SLOT(dlabel);
1877
1878	if (!mac_biba_dominate_single(subj, obj))
1879		return (EACCES);
1880
1881	if (vp != NULL) {
1882		obj = SLOT(label);
1883
1884		if (!mac_biba_dominate_single(subj, obj))
1885			return (EACCES);
1886	}
1887
1888	return (0);
1889}
1890
1891static int
1892mac_biba_check_vnode_revoke(struct ucred *cred, struct vnode *vp,
1893    struct label *label)
1894{
1895	struct mac_biba *subj, *obj;
1896
1897	if (!mac_biba_enabled)
1898		return (0);
1899
1900	subj = SLOT(&cred->cr_label);
1901	obj = SLOT(label);
1902
1903	if (!mac_biba_dominate_single(subj, obj))
1904		return (EACCES);
1905
1906	return (0);
1907}
1908
1909static int
1910mac_biba_check_vnode_setacl(struct ucred *cred, struct vnode *vp,
1911    struct label *label, acl_type_t type, struct acl *acl)
1912{
1913	struct mac_biba *subj, *obj;
1914
1915	if (!mac_biba_enabled)
1916		return (0);
1917
1918	subj = SLOT(&cred->cr_label);
1919	obj = SLOT(label);
1920
1921	if (!mac_biba_dominate_single(subj, obj))
1922		return (EACCES);
1923
1924	return (0);
1925}
1926
1927static int
1928mac_biba_check_vnode_setextattr(struct ucred *cred, struct vnode *vp,
1929    struct label *vnodelabel, int attrnamespace, const char *name,
1930    struct uio *uio)
1931{
1932	struct mac_biba *subj, *obj;
1933
1934	if (!mac_biba_enabled)
1935		return (0);
1936
1937	subj = SLOT(&cred->cr_label);
1938	obj = SLOT(vnodelabel);
1939
1940	if (!mac_biba_dominate_single(subj, obj))
1941		return (EACCES);
1942
1943	/* XXX: protect the MAC EA in a special way? */
1944
1945	return (0);
1946}
1947
1948static int
1949mac_biba_check_vnode_setflags(struct ucred *cred, struct vnode *vp,
1950    struct label *vnodelabel, u_long flags)
1951{
1952	struct mac_biba *subj, *obj;
1953
1954	if (!mac_biba_enabled)
1955		return (0);
1956
1957	subj = SLOT(&cred->cr_label);
1958	obj = SLOT(vnodelabel);
1959
1960	if (!mac_biba_dominate_single(subj, obj))
1961		return (EACCES);
1962
1963	return (0);
1964}
1965
1966static int
1967mac_biba_check_vnode_setmode(struct ucred *cred, struct vnode *vp,
1968    struct label *vnodelabel, mode_t mode)
1969{
1970	struct mac_biba *subj, *obj;
1971
1972	if (!mac_biba_enabled)
1973		return (0);
1974
1975	subj = SLOT(&cred->cr_label);
1976	obj = SLOT(vnodelabel);
1977
1978	if (!mac_biba_dominate_single(subj, obj))
1979		return (EACCES);
1980
1981	return (0);
1982}
1983
1984static int
1985mac_biba_check_vnode_setowner(struct ucred *cred, struct vnode *vp,
1986    struct label *vnodelabel, uid_t uid, gid_t gid)
1987{
1988	struct mac_biba *subj, *obj;
1989
1990	if (!mac_biba_enabled)
1991		return (0);
1992
1993	subj = SLOT(&cred->cr_label);
1994	obj = SLOT(vnodelabel);
1995
1996	if (!mac_biba_dominate_single(subj, obj))
1997		return (EACCES);
1998
1999	return (0);
2000}
2001
2002static int
2003mac_biba_check_vnode_setutimes(struct ucred *cred, struct vnode *vp,
2004    struct label *vnodelabel, struct timespec atime, struct timespec mtime)
2005{
2006	struct mac_biba *subj, *obj;
2007
2008	if (!mac_biba_enabled)
2009		return (0);
2010
2011	subj = SLOT(&cred->cr_label);
2012	obj = SLOT(vnodelabel);
2013
2014	if (!mac_biba_dominate_single(subj, obj))
2015		return (EACCES);
2016
2017	return (0);
2018}
2019
2020static int
2021mac_biba_check_vnode_stat(struct ucred *active_cred, struct ucred *file_cred,
2022    struct vnode *vp, struct label *vnodelabel)
2023{
2024	struct mac_biba *subj, *obj;
2025
2026	if (!mac_biba_enabled)
2027		return (0);
2028
2029	subj = SLOT(&active_cred->cr_label);
2030	obj = SLOT(vnodelabel);
2031
2032	if (!mac_biba_dominate_single(obj, subj))
2033		return (EACCES);
2034
2035	return (0);
2036}
2037
2038static int
2039mac_biba_check_vnode_write(struct ucred *active_cred,
2040    struct ucred *file_cred, struct vnode *vp, struct label *label)
2041{
2042	struct mac_biba *subj, *obj;
2043
2044	if (!mac_biba_enabled || !mac_biba_revocation_enabled)
2045		return (0);
2046
2047	subj = SLOT(&active_cred->cr_label);
2048	obj = SLOT(label);
2049
2050	if (!mac_biba_dominate_single(subj, obj))
2051		return (EACCES);
2052
2053	return (0);
2054}
2055
2056static vm_prot_t
2057mac_biba_check_vnode_mmap_perms(struct ucred *cred, struct vnode *vp,
2058    struct label *label, int newmapping)
2059{
2060	struct mac_biba *subj, *obj;
2061	vm_prot_t prot = 0;
2062
2063	if (!mac_biba_enabled || (!mac_biba_revocation_enabled && !newmapping))
2064		return (VM_PROT_ALL);
2065
2066	subj = SLOT(&cred->cr_label);
2067	obj = SLOT(label);
2068
2069	if (mac_biba_dominate_single(obj, subj))
2070		prot |= VM_PROT_READ | VM_PROT_EXECUTE;
2071	if (mac_biba_dominate_single(subj, obj))
2072		prot |= VM_PROT_WRITE;
2073	return (prot);
2074}
2075
2076static struct mac_policy_op_entry mac_biba_ops[] =
2077{
2078	{ MAC_DESTROY,
2079	    (macop_t)mac_biba_destroy },
2080	{ MAC_INIT,
2081	    (macop_t)mac_biba_init },
2082	{ MAC_INIT_BPFDESC,
2083	    (macop_t)mac_biba_init_bpfdesc },
2084	{ MAC_INIT_CRED,
2085	    (macop_t)mac_biba_init_cred },
2086	{ MAC_INIT_DEVFSDIRENT,
2087	    (macop_t)mac_biba_init_devfsdirent },
2088	{ MAC_INIT_IFNET,
2089	    (macop_t)mac_biba_init_ifnet },
2090	{ MAC_INIT_IPQ,
2091	    (macop_t)mac_biba_init_ipq },
2092	{ MAC_INIT_MBUF,
2093	    (macop_t)mac_biba_init_mbuf },
2094	{ MAC_INIT_MOUNT,
2095	    (macop_t)mac_biba_init_mount },
2096	{ MAC_INIT_PIPE,
2097	    (macop_t)mac_biba_init_pipe },
2098	{ MAC_INIT_SOCKET,
2099	    (macop_t)mac_biba_init_socket },
2100	{ MAC_INIT_TEMP,
2101	    (macop_t)mac_biba_init_temp },
2102	{ MAC_INIT_VNODE,
2103	    (macop_t)mac_biba_init_vnode },
2104	{ MAC_DESTROY_BPFDESC,
2105	    (macop_t)mac_biba_destroy_bpfdesc },
2106	{ MAC_DESTROY_CRED,
2107	    (macop_t)mac_biba_destroy_cred },
2108	{ MAC_DESTROY_DEVFSDIRENT,
2109	    (macop_t)mac_biba_destroy_devfsdirent },
2110	{ MAC_DESTROY_IFNET,
2111	    (macop_t)mac_biba_destroy_ifnet },
2112	{ MAC_DESTROY_IPQ,
2113	    (macop_t)mac_biba_destroy_ipq },
2114	{ MAC_DESTROY_MBUF,
2115	    (macop_t)mac_biba_destroy_mbuf },
2116	{ MAC_DESTROY_MOUNT,
2117	    (macop_t)mac_biba_destroy_mount },
2118	{ MAC_DESTROY_PIPE,
2119	    (macop_t)mac_biba_destroy_pipe },
2120	{ MAC_DESTROY_SOCKET,
2121	    (macop_t)mac_biba_destroy_socket },
2122	{ MAC_DESTROY_TEMP,
2123	    (macop_t)mac_biba_destroy_temp },
2124	{ MAC_DESTROY_VNODE,
2125	    (macop_t)mac_biba_destroy_vnode },
2126	{ MAC_EXTERNALIZE,
2127	    (macop_t)mac_biba_externalize },
2128	{ MAC_INTERNALIZE,
2129	    (macop_t)mac_biba_internalize },
2130	{ MAC_CREATE_DEVFS_DEVICE,
2131	    (macop_t)mac_biba_create_devfs_device },
2132	{ MAC_CREATE_DEVFS_DIRECTORY,
2133	    (macop_t)mac_biba_create_devfs_directory },
2134	{ MAC_CREATE_DEVFS_VNODE,
2135	    (macop_t)mac_biba_create_devfs_vnode },
2136	{ MAC_CREATE_VNODE,
2137	    (macop_t)mac_biba_create_vnode },
2138	{ MAC_CREATE_MOUNT,
2139	    (macop_t)mac_biba_create_mount },
2140	{ MAC_CREATE_ROOT_MOUNT,
2141	    (macop_t)mac_biba_create_root_mount },
2142	{ MAC_RELABEL_VNODE,
2143	    (macop_t)mac_biba_relabel_vnode },
2144	{ MAC_UPDATE_DEVFSDIRENT,
2145	    (macop_t)mac_biba_update_devfsdirent },
2146	{ MAC_UPDATE_PROCFSVNODE,
2147	    (macop_t)mac_biba_update_procfsvnode },
2148	{ MAC_UPDATE_VNODE_FROM_EXTERNALIZED,
2149	    (macop_t)mac_biba_update_vnode_from_externalized },
2150	{ MAC_UPDATE_VNODE_FROM_MOUNT,
2151	    (macop_t)mac_biba_update_vnode_from_mount },
2152	{ MAC_CREATE_MBUF_FROM_SOCKET,
2153	    (macop_t)mac_biba_create_mbuf_from_socket },
2154	{ MAC_CREATE_PIPE,
2155	    (macop_t)mac_biba_create_pipe },
2156	{ MAC_CREATE_SOCKET,
2157	    (macop_t)mac_biba_create_socket },
2158	{ MAC_CREATE_SOCKET_FROM_SOCKET,
2159	    (macop_t)mac_biba_create_socket_from_socket },
2160	{ MAC_RELABEL_PIPE,
2161	    (macop_t)mac_biba_relabel_pipe },
2162	{ MAC_RELABEL_SOCKET,
2163	    (macop_t)mac_biba_relabel_socket },
2164	{ MAC_SET_SOCKET_PEER_FROM_MBUF,
2165	    (macop_t)mac_biba_set_socket_peer_from_mbuf },
2166	{ MAC_SET_SOCKET_PEER_FROM_SOCKET,
2167	    (macop_t)mac_biba_set_socket_peer_from_socket },
2168	{ MAC_CREATE_BPFDESC,
2169	    (macop_t)mac_biba_create_bpfdesc },
2170	{ MAC_CREATE_DATAGRAM_FROM_IPQ,
2171	    (macop_t)mac_biba_create_datagram_from_ipq },
2172	{ MAC_CREATE_FRAGMENT,
2173	    (macop_t)mac_biba_create_fragment },
2174	{ MAC_CREATE_IFNET,
2175	    (macop_t)mac_biba_create_ifnet },
2176	{ MAC_CREATE_IPQ,
2177	    (macop_t)mac_biba_create_ipq },
2178	{ MAC_CREATE_MBUF_FROM_MBUF,
2179	    (macop_t)mac_biba_create_mbuf_from_mbuf },
2180	{ MAC_CREATE_MBUF_LINKLAYER,
2181	    (macop_t)mac_biba_create_mbuf_linklayer },
2182	{ MAC_CREATE_MBUF_FROM_BPFDESC,
2183	    (macop_t)mac_biba_create_mbuf_from_bpfdesc },
2184	{ MAC_CREATE_MBUF_FROM_IFNET,
2185	    (macop_t)mac_biba_create_mbuf_from_ifnet },
2186	{ MAC_CREATE_MBUF_MULTICAST_ENCAP,
2187	    (macop_t)mac_biba_create_mbuf_multicast_encap },
2188	{ MAC_CREATE_MBUF_NETLAYER,
2189	    (macop_t)mac_biba_create_mbuf_netlayer },
2190	{ MAC_FRAGMENT_MATCH,
2191	    (macop_t)mac_biba_fragment_match },
2192	{ MAC_RELABEL_IFNET,
2193	    (macop_t)mac_biba_relabel_ifnet },
2194	{ MAC_UPDATE_IPQ,
2195	    (macop_t)mac_biba_update_ipq },
2196	{ MAC_CREATE_CRED,
2197	    (macop_t)mac_biba_create_cred },
2198	{ MAC_EXECVE_TRANSITION,
2199	    (macop_t)mac_biba_execve_transition },
2200	{ MAC_EXECVE_WILL_TRANSITION,
2201	    (macop_t)mac_biba_execve_will_transition },
2202	{ MAC_CREATE_PROC0,
2203	    (macop_t)mac_biba_create_proc0 },
2204	{ MAC_CREATE_PROC1,
2205	    (macop_t)mac_biba_create_proc1 },
2206	{ MAC_RELABEL_CRED,
2207	    (macop_t)mac_biba_relabel_cred },
2208	{ MAC_CHECK_BPFDESC_RECEIVE,
2209	    (macop_t)mac_biba_check_bpfdesc_receive },
2210	{ MAC_CHECK_CRED_RELABEL,
2211	    (macop_t)mac_biba_check_cred_relabel },
2212	{ MAC_CHECK_CRED_VISIBLE,
2213	    (macop_t)mac_biba_check_cred_visible },
2214	{ MAC_CHECK_IFNET_RELABEL,
2215	    (macop_t)mac_biba_check_ifnet_relabel },
2216	{ MAC_CHECK_IFNET_TRANSMIT,
2217	    (macop_t)mac_biba_check_ifnet_transmit },
2218	{ MAC_CHECK_MOUNT_STAT,
2219	    (macop_t)mac_biba_check_mount_stat },
2220	{ MAC_CHECK_PIPE_IOCTL,
2221	    (macop_t)mac_biba_check_pipe_ioctl },
2222	{ MAC_CHECK_PIPE_POLL,
2223	    (macop_t)mac_biba_check_pipe_poll },
2224	{ MAC_CHECK_PIPE_READ,
2225	    (macop_t)mac_biba_check_pipe_read },
2226	{ MAC_CHECK_PIPE_RELABEL,
2227	    (macop_t)mac_biba_check_pipe_relabel },
2228	{ MAC_CHECK_PIPE_STAT,
2229	    (macop_t)mac_biba_check_pipe_stat },
2230	{ MAC_CHECK_PIPE_WRITE,
2231	    (macop_t)mac_biba_check_pipe_write },
2232	{ MAC_CHECK_PROC_DEBUG,
2233	    (macop_t)mac_biba_check_proc_debug },
2234	{ MAC_CHECK_PROC_SCHED,
2235	    (macop_t)mac_biba_check_proc_sched },
2236	{ MAC_CHECK_PROC_SIGNAL,
2237	    (macop_t)mac_biba_check_proc_signal },
2238	{ MAC_CHECK_SOCKET_DELIVER,
2239	    (macop_t)mac_biba_check_socket_deliver },
2240	{ MAC_CHECK_SOCKET_RELABEL,
2241	    (macop_t)mac_biba_check_socket_relabel },
2242	{ MAC_CHECK_SOCKET_VISIBLE,
2243	    (macop_t)mac_biba_check_socket_visible },
2244	{ MAC_CHECK_VNODE_ACCESS,
2245	    (macop_t)mac_biba_check_vnode_access },
2246	{ MAC_CHECK_VNODE_CHDIR,
2247	    (macop_t)mac_biba_check_vnode_chdir },
2248	{ MAC_CHECK_VNODE_CHROOT,
2249	    (macop_t)mac_biba_check_vnode_chroot },
2250	{ MAC_CHECK_VNODE_CREATE,
2251	    (macop_t)mac_biba_check_vnode_create },
2252	{ MAC_CHECK_VNODE_DELETE,
2253	    (macop_t)mac_biba_check_vnode_delete },
2254	{ MAC_CHECK_VNODE_DELETEACL,
2255	    (macop_t)mac_biba_check_vnode_deleteacl },
2256	{ MAC_CHECK_VNODE_EXEC,
2257	    (macop_t)mac_biba_check_vnode_exec },
2258	{ MAC_CHECK_VNODE_GETACL,
2259	    (macop_t)mac_biba_check_vnode_getacl },
2260	{ MAC_CHECK_VNODE_GETEXTATTR,
2261	    (macop_t)mac_biba_check_vnode_getextattr },
2262	{ MAC_CHECK_VNODE_LOOKUP,
2263	    (macop_t)mac_biba_check_vnode_lookup },
2264	{ MAC_CHECK_VNODE_OPEN,
2265	    (macop_t)mac_biba_check_vnode_open },
2266	{ MAC_CHECK_VNODE_POLL,
2267	    (macop_t)mac_biba_check_vnode_poll },
2268	{ MAC_CHECK_VNODE_READ,
2269	    (macop_t)mac_biba_check_vnode_read },
2270	{ MAC_CHECK_VNODE_READDIR,
2271	    (macop_t)mac_biba_check_vnode_readdir },
2272	{ MAC_CHECK_VNODE_READLINK,
2273	    (macop_t)mac_biba_check_vnode_readlink },
2274	{ MAC_CHECK_VNODE_RELABEL,
2275	    (macop_t)mac_biba_check_vnode_relabel },
2276	{ MAC_CHECK_VNODE_RENAME_FROM,
2277	    (macop_t)mac_biba_check_vnode_rename_from },
2278	{ MAC_CHECK_VNODE_RENAME_TO,
2279	    (macop_t)mac_biba_check_vnode_rename_to },
2280	{ MAC_CHECK_VNODE_REVOKE,
2281	    (macop_t)mac_biba_check_vnode_revoke },
2282	{ MAC_CHECK_VNODE_SETACL,
2283	    (macop_t)mac_biba_check_vnode_setacl },
2284	{ MAC_CHECK_VNODE_SETEXTATTR,
2285	    (macop_t)mac_biba_check_vnode_setextattr },
2286	{ MAC_CHECK_VNODE_SETFLAGS,
2287	    (macop_t)mac_biba_check_vnode_setflags },
2288	{ MAC_CHECK_VNODE_SETMODE,
2289	    (macop_t)mac_biba_check_vnode_setmode },
2290	{ MAC_CHECK_VNODE_SETOWNER,
2291	    (macop_t)mac_biba_check_vnode_setowner },
2292	{ MAC_CHECK_VNODE_SETUTIMES,
2293	    (macop_t)mac_biba_check_vnode_setutimes },
2294	{ MAC_CHECK_VNODE_STAT,
2295	    (macop_t)mac_biba_check_vnode_stat },
2296	{ MAC_CHECK_VNODE_WRITE,
2297	    (macop_t)mac_biba_check_vnode_write },
2298	{ MAC_CHECK_VNODE_MMAP_PERMS,
2299	    (macop_t)mac_biba_check_vnode_mmap_perms },
2300	{ MAC_OP_LAST, NULL }
2301};
2302
2303MAC_POLICY_SET(mac_biba_ops, trustedbsd_mac_biba, "TrustedBSD MAC/Biba",
2304    MPC_LOADTIME_FLAG_NOTLATE, &mac_biba_slot);
2305