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