1 /*- 2 * Copyright (c) 1999-2002, 2007-2011 Robert N. M. Watson 3 * Copyright (c) 2001-2005 McAfee, Inc. 4 * Copyright (c) 2006 SPARTA, Inc. 5 * All rights reserved. 6 * 7 * This software was developed by Robert Watson for the TrustedBSD Project. 8 * 9 * This software was developed for the FreeBSD Project in part by McAfee 10 * Research, the Security Research Division of McAfee, Inc. under 11 * DARPA/SPAWAR contract N66001-01-C-8035 ("CBOSS"), as part of the DARPA 12 * CHATS research program. 13 * 14 * This software was enhanced by SPARTA ISSO under SPAWAR contract 15 * N66001-04-C-6019 ("SEFOS"). 16 * 17 * This software was developed at the University of Cambridge Computer 18 * Laboratory with support from a grant from Google, Inc. 19 * 20 * Redistribution and use in source and binary forms, with or without 21 * modification, are permitted provided that the following conditions 22 * are met: 23 * 1. Redistributions of source code must retain the above copyright 24 * notice, this list of conditions and the following disclaimer. 25 * 2. Redistributions in binary form must reproduce the above copyright 26 * notice, this list of conditions and the following disclaimer in the 27 * documentation and/or other materials provided with the distribution. 28 * 29 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 30 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 31 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 32 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 33 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 34 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 35 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 36 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 37 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 38 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 39 * SUCH DAMAGE. 40 * 41 * $FreeBSD$ 42 */ 43 44 /* 45 * Developed by the TrustedBSD Project. 46 * 47 * Biba fixed label mandatory integrity policy. 48 */ 49 50 #include <sys/param.h> 51 #include <sys/conf.h> 52 #include <sys/extattr.h> 53 #include <sys/kernel.h> 54 #include <sys/ksem.h> 55 #include <sys/malloc.h> 56 #include <sys/mman.h> 57 #include <sys/mount.h> 58 #include <sys/priv.h> 59 #include <sys/proc.h> 60 #include <sys/sbuf.h> 61 #include <sys/systm.h> 62 #include <sys/sysproto.h> 63 #include <sys/sysent.h> 64 #include <sys/systm.h> 65 #include <sys/vnode.h> 66 #include <sys/file.h> 67 #include <sys/socket.h> 68 #include <sys/socketvar.h> 69 #include <sys/pipe.h> 70 #include <sys/sx.h> 71 #include <sys/sysctl.h> 72 #include <sys/msg.h> 73 #include <sys/sem.h> 74 #include <sys/shm.h> 75 76 #include <fs/devfs/devfs.h> 77 78 #include <net/bpfdesc.h> 79 #include <net/if.h> 80 #include <net/if_types.h> 81 #include <net/if_var.h> 82 83 #include <netinet/in.h> 84 #include <netinet/in_pcb.h> 85 #include <netinet/ip_var.h> 86 87 #include <vm/uma.h> 88 #include <vm/vm.h> 89 90 #include <security/mac/mac_policy.h> 91 #include <security/mac_biba/mac_biba.h> 92 93 SYSCTL_DECL(_security_mac); 94 95 static SYSCTL_NODE(_security_mac, OID_AUTO, biba, CTLFLAG_RW, 0, 96 "TrustedBSD mac_biba policy controls"); 97 98 static int biba_label_size = sizeof(struct mac_biba); 99 SYSCTL_INT(_security_mac_biba, OID_AUTO, label_size, CTLFLAG_RD, 100 &biba_label_size, 0, "Size of struct mac_biba"); 101 102 static int biba_enabled = 1; 103 SYSCTL_INT(_security_mac_biba, OID_AUTO, enabled, CTLFLAG_RW, &biba_enabled, 104 0, "Enforce MAC/Biba policy"); 105 TUNABLE_INT("security.mac.biba.enabled", &biba_enabled); 106 107 static int destroyed_not_inited; 108 SYSCTL_INT(_security_mac_biba, OID_AUTO, destroyed_not_inited, CTLFLAG_RD, 109 &destroyed_not_inited, 0, "Count of labels destroyed but not inited"); 110 111 static int trust_all_interfaces = 0; 112 SYSCTL_INT(_security_mac_biba, OID_AUTO, trust_all_interfaces, CTLFLAG_RD, 113 &trust_all_interfaces, 0, "Consider all interfaces 'trusted' by MAC/Biba"); 114 TUNABLE_INT("security.mac.biba.trust_all_interfaces", &trust_all_interfaces); 115 116 static char trusted_interfaces[128]; 117 SYSCTL_STRING(_security_mac_biba, OID_AUTO, trusted_interfaces, CTLFLAG_RD, 118 trusted_interfaces, 0, "Interfaces considered 'trusted' by MAC/Biba"); 119 TUNABLE_STR("security.mac.biba.trusted_interfaces", trusted_interfaces, 120 sizeof(trusted_interfaces)); 121 122 static int max_compartments = MAC_BIBA_MAX_COMPARTMENTS; 123 SYSCTL_INT(_security_mac_biba, OID_AUTO, max_compartments, CTLFLAG_RD, 124 &max_compartments, 0, "Maximum supported compartments"); 125 126 static int ptys_equal = 0; 127 SYSCTL_INT(_security_mac_biba, OID_AUTO, ptys_equal, CTLFLAG_RW, &ptys_equal, 128 0, "Label pty devices as biba/equal on create"); 129 TUNABLE_INT("security.mac.biba.ptys_equal", &ptys_equal); 130 131 static int interfaces_equal = 1; 132 SYSCTL_INT(_security_mac_biba, OID_AUTO, interfaces_equal, CTLFLAG_RW, 133 &interfaces_equal, 0, "Label network interfaces as biba/equal on create"); 134 TUNABLE_INT("security.mac.biba.interfaces_equal", &interfaces_equal); 135 136 static int revocation_enabled = 0; 137 SYSCTL_INT(_security_mac_biba, OID_AUTO, revocation_enabled, CTLFLAG_RW, 138 &revocation_enabled, 0, "Revoke access to objects on relabel"); 139 TUNABLE_INT("security.mac.biba.revocation_enabled", &revocation_enabled); 140 141 static int biba_slot; 142 #define SLOT(l) ((struct mac_biba *)mac_label_get((l), biba_slot)) 143 #define SLOT_SET(l, val) mac_label_set((l), biba_slot, (uintptr_t)(val)) 144 145 static uma_zone_t zone_biba; 146 147 static __inline int 148 biba_bit_set_empty(u_char *set) { 149 int i; 150 151 for (i = 0; i < MAC_BIBA_MAX_COMPARTMENTS >> 3; i++) 152 if (set[i] != 0) 153 return (0); 154 return (1); 155 } 156 157 static struct mac_biba * 158 biba_alloc(int flag) 159 { 160 161 return (uma_zalloc(zone_biba, flag | M_ZERO)); 162 } 163 164 static void 165 biba_free(struct mac_biba *mb) 166 { 167 168 if (mb != NULL) 169 uma_zfree(zone_biba, mb); 170 else 171 atomic_add_int(&destroyed_not_inited, 1); 172 } 173 174 static int 175 biba_atmostflags(struct mac_biba *mb, int flags) 176 { 177 178 if ((mb->mb_flags & flags) != mb->mb_flags) 179 return (EINVAL); 180 return (0); 181 } 182 183 static int 184 biba_dominate_element(struct mac_biba_element *a, struct mac_biba_element *b) 185 { 186 int bit; 187 188 switch (a->mbe_type) { 189 case MAC_BIBA_TYPE_EQUAL: 190 case MAC_BIBA_TYPE_HIGH: 191 return (1); 192 193 case MAC_BIBA_TYPE_LOW: 194 switch (b->mbe_type) { 195 case MAC_BIBA_TYPE_GRADE: 196 case MAC_BIBA_TYPE_HIGH: 197 return (0); 198 199 case MAC_BIBA_TYPE_EQUAL: 200 case MAC_BIBA_TYPE_LOW: 201 return (1); 202 203 default: 204 panic("biba_dominate_element: b->mbe_type invalid"); 205 } 206 207 case MAC_BIBA_TYPE_GRADE: 208 switch (b->mbe_type) { 209 case MAC_BIBA_TYPE_EQUAL: 210 case MAC_BIBA_TYPE_LOW: 211 return (1); 212 213 case MAC_BIBA_TYPE_HIGH: 214 return (0); 215 216 case MAC_BIBA_TYPE_GRADE: 217 for (bit = 1; bit <= MAC_BIBA_MAX_COMPARTMENTS; bit++) 218 if (!MAC_BIBA_BIT_TEST(bit, 219 a->mbe_compartments) && 220 MAC_BIBA_BIT_TEST(bit, b->mbe_compartments)) 221 return (0); 222 return (a->mbe_grade >= b->mbe_grade); 223 224 default: 225 panic("biba_dominate_element: b->mbe_type invalid"); 226 } 227 228 default: 229 panic("biba_dominate_element: a->mbe_type invalid"); 230 } 231 232 return (0); 233 } 234 235 static int 236 biba_subject_dominate_high(struct mac_biba *mb) 237 { 238 struct mac_biba_element *element; 239 240 KASSERT((mb->mb_flags & MAC_BIBA_FLAG_EFFECTIVE) != 0, 241 ("biba_effective_in_range: mb not effective")); 242 element = &mb->mb_effective; 243 244 return (element->mbe_type == MAC_BIBA_TYPE_EQUAL || 245 element->mbe_type == MAC_BIBA_TYPE_HIGH); 246 } 247 248 static int 249 biba_range_in_range(struct mac_biba *rangea, struct mac_biba *rangeb) 250 { 251 252 return (biba_dominate_element(&rangeb->mb_rangehigh, 253 &rangea->mb_rangehigh) && 254 biba_dominate_element(&rangea->mb_rangelow, 255 &rangeb->mb_rangelow)); 256 } 257 258 static int 259 biba_effective_in_range(struct mac_biba *effective, struct mac_biba *range) 260 { 261 262 KASSERT((effective->mb_flags & MAC_BIBA_FLAG_EFFECTIVE) != 0, 263 ("biba_effective_in_range: a not effective")); 264 KASSERT((range->mb_flags & MAC_BIBA_FLAG_RANGE) != 0, 265 ("biba_effective_in_range: b not range")); 266 267 return (biba_dominate_element(&range->mb_rangehigh, 268 &effective->mb_effective) && 269 biba_dominate_element(&effective->mb_effective, 270 &range->mb_rangelow)); 271 272 return (1); 273 } 274 275 static int 276 biba_dominate_effective(struct mac_biba *a, struct mac_biba *b) 277 { 278 KASSERT((a->mb_flags & MAC_BIBA_FLAG_EFFECTIVE) != 0, 279 ("biba_dominate_effective: a not effective")); 280 KASSERT((b->mb_flags & MAC_BIBA_FLAG_EFFECTIVE) != 0, 281 ("biba_dominate_effective: b not effective")); 282 283 return (biba_dominate_element(&a->mb_effective, &b->mb_effective)); 284 } 285 286 static int 287 biba_equal_element(struct mac_biba_element *a, struct mac_biba_element *b) 288 { 289 290 if (a->mbe_type == MAC_BIBA_TYPE_EQUAL || 291 b->mbe_type == MAC_BIBA_TYPE_EQUAL) 292 return (1); 293 294 return (a->mbe_type == b->mbe_type && a->mbe_grade == b->mbe_grade); 295 } 296 297 static int 298 biba_equal_effective(struct mac_biba *a, struct mac_biba *b) 299 { 300 301 KASSERT((a->mb_flags & MAC_BIBA_FLAG_EFFECTIVE) != 0, 302 ("biba_equal_effective: a not effective")); 303 KASSERT((b->mb_flags & MAC_BIBA_FLAG_EFFECTIVE) != 0, 304 ("biba_equal_effective: b not effective")); 305 306 return (biba_equal_element(&a->mb_effective, &b->mb_effective)); 307 } 308 309 static int 310 biba_contains_equal(struct mac_biba *mb) 311 { 312 313 if (mb->mb_flags & MAC_BIBA_FLAG_EFFECTIVE) { 314 if (mb->mb_effective.mbe_type == MAC_BIBA_TYPE_EQUAL) 315 return (1); 316 } 317 318 if (mb->mb_flags & MAC_BIBA_FLAG_RANGE) { 319 if (mb->mb_rangelow.mbe_type == MAC_BIBA_TYPE_EQUAL) 320 return (1); 321 if (mb->mb_rangehigh.mbe_type == MAC_BIBA_TYPE_EQUAL) 322 return (1); 323 } 324 325 return (0); 326 } 327 328 static int 329 biba_subject_privileged(struct mac_biba *mb) 330 { 331 332 KASSERT((mb->mb_flags & MAC_BIBA_FLAGS_BOTH) == MAC_BIBA_FLAGS_BOTH, 333 ("biba_subject_privileged: subject doesn't have both labels")); 334 335 /* If the effective is EQUAL, it's ok. */ 336 if (mb->mb_effective.mbe_type == MAC_BIBA_TYPE_EQUAL) 337 return (0); 338 339 /* If either range endpoint is EQUAL, it's ok. */ 340 if (mb->mb_rangelow.mbe_type == MAC_BIBA_TYPE_EQUAL || 341 mb->mb_rangehigh.mbe_type == MAC_BIBA_TYPE_EQUAL) 342 return (0); 343 344 /* If the range is low-high, it's ok. */ 345 if (mb->mb_rangelow.mbe_type == MAC_BIBA_TYPE_LOW && 346 mb->mb_rangehigh.mbe_type == MAC_BIBA_TYPE_HIGH) 347 return (0); 348 349 /* It's not ok. */ 350 return (EPERM); 351 } 352 353 static int 354 biba_high_effective(struct mac_biba *mb) 355 { 356 357 KASSERT((mb->mb_flags & MAC_BIBA_FLAG_EFFECTIVE) != 0, 358 ("biba_equal_effective: mb not effective")); 359 360 return (mb->mb_effective.mbe_type == MAC_BIBA_TYPE_HIGH); 361 } 362 363 static int 364 biba_valid(struct mac_biba *mb) 365 { 366 367 if (mb->mb_flags & MAC_BIBA_FLAG_EFFECTIVE) { 368 switch (mb->mb_effective.mbe_type) { 369 case MAC_BIBA_TYPE_GRADE: 370 break; 371 372 case MAC_BIBA_TYPE_EQUAL: 373 case MAC_BIBA_TYPE_HIGH: 374 case MAC_BIBA_TYPE_LOW: 375 if (mb->mb_effective.mbe_grade != 0 || 376 !MAC_BIBA_BIT_SET_EMPTY( 377 mb->mb_effective.mbe_compartments)) 378 return (EINVAL); 379 break; 380 381 default: 382 return (EINVAL); 383 } 384 } else { 385 if (mb->mb_effective.mbe_type != MAC_BIBA_TYPE_UNDEF) 386 return (EINVAL); 387 } 388 389 if (mb->mb_flags & MAC_BIBA_FLAG_RANGE) { 390 switch (mb->mb_rangelow.mbe_type) { 391 case MAC_BIBA_TYPE_GRADE: 392 break; 393 394 case MAC_BIBA_TYPE_EQUAL: 395 case MAC_BIBA_TYPE_HIGH: 396 case MAC_BIBA_TYPE_LOW: 397 if (mb->mb_rangelow.mbe_grade != 0 || 398 !MAC_BIBA_BIT_SET_EMPTY( 399 mb->mb_rangelow.mbe_compartments)) 400 return (EINVAL); 401 break; 402 403 default: 404 return (EINVAL); 405 } 406 407 switch (mb->mb_rangehigh.mbe_type) { 408 case MAC_BIBA_TYPE_GRADE: 409 break; 410 411 case MAC_BIBA_TYPE_EQUAL: 412 case MAC_BIBA_TYPE_HIGH: 413 case MAC_BIBA_TYPE_LOW: 414 if (mb->mb_rangehigh.mbe_grade != 0 || 415 !MAC_BIBA_BIT_SET_EMPTY( 416 mb->mb_rangehigh.mbe_compartments)) 417 return (EINVAL); 418 break; 419 420 default: 421 return (EINVAL); 422 } 423 if (!biba_dominate_element(&mb->mb_rangehigh, 424 &mb->mb_rangelow)) 425 return (EINVAL); 426 } else { 427 if (mb->mb_rangelow.mbe_type != MAC_BIBA_TYPE_UNDEF || 428 mb->mb_rangehigh.mbe_type != MAC_BIBA_TYPE_UNDEF) 429 return (EINVAL); 430 } 431 432 return (0); 433 } 434 435 static void 436 biba_set_range(struct mac_biba *mb, u_short typelow, u_short gradelow, 437 u_char *compartmentslow, u_short typehigh, u_short gradehigh, 438 u_char *compartmentshigh) 439 { 440 441 mb->mb_rangelow.mbe_type = typelow; 442 mb->mb_rangelow.mbe_grade = gradelow; 443 if (compartmentslow != NULL) 444 memcpy(mb->mb_rangelow.mbe_compartments, compartmentslow, 445 sizeof(mb->mb_rangelow.mbe_compartments)); 446 mb->mb_rangehigh.mbe_type = typehigh; 447 mb->mb_rangehigh.mbe_grade = gradehigh; 448 if (compartmentshigh != NULL) 449 memcpy(mb->mb_rangehigh.mbe_compartments, compartmentshigh, 450 sizeof(mb->mb_rangehigh.mbe_compartments)); 451 mb->mb_flags |= MAC_BIBA_FLAG_RANGE; 452 } 453 454 static void 455 biba_set_effective(struct mac_biba *mb, u_short type, u_short grade, 456 u_char *compartments) 457 { 458 459 mb->mb_effective.mbe_type = type; 460 mb->mb_effective.mbe_grade = grade; 461 if (compartments != NULL) 462 memcpy(mb->mb_effective.mbe_compartments, compartments, 463 sizeof(mb->mb_effective.mbe_compartments)); 464 mb->mb_flags |= MAC_BIBA_FLAG_EFFECTIVE; 465 } 466 467 static void 468 biba_copy_range(struct mac_biba *labelfrom, struct mac_biba *labelto) 469 { 470 471 KASSERT((labelfrom->mb_flags & MAC_BIBA_FLAG_RANGE) != 0, 472 ("biba_copy_range: labelfrom not range")); 473 474 labelto->mb_rangelow = labelfrom->mb_rangelow; 475 labelto->mb_rangehigh = labelfrom->mb_rangehigh; 476 labelto->mb_flags |= MAC_BIBA_FLAG_RANGE; 477 } 478 479 static void 480 biba_copy_effective(struct mac_biba *labelfrom, struct mac_biba *labelto) 481 { 482 483 KASSERT((labelfrom->mb_flags & MAC_BIBA_FLAG_EFFECTIVE) != 0, 484 ("biba_copy_effective: labelfrom not effective")); 485 486 labelto->mb_effective = labelfrom->mb_effective; 487 labelto->mb_flags |= MAC_BIBA_FLAG_EFFECTIVE; 488 } 489 490 static void 491 biba_copy(struct mac_biba *source, struct mac_biba *dest) 492 { 493 494 if (source->mb_flags & MAC_BIBA_FLAG_EFFECTIVE) 495 biba_copy_effective(source, dest); 496 if (source->mb_flags & MAC_BIBA_FLAG_RANGE) 497 biba_copy_range(source, dest); 498 } 499 500 /* 501 * Policy module operations. 502 */ 503 static void 504 biba_init(struct mac_policy_conf *conf) 505 { 506 507 zone_biba = uma_zcreate("mac_biba", sizeof(struct mac_biba), NULL, 508 NULL, NULL, NULL, UMA_ALIGN_PTR, 0); 509 } 510 511 /* 512 * Label operations. 513 */ 514 static void 515 biba_init_label(struct label *label) 516 { 517 518 SLOT_SET(label, biba_alloc(M_WAITOK)); 519 } 520 521 static int 522 biba_init_label_waitcheck(struct label *label, int flag) 523 { 524 525 SLOT_SET(label, biba_alloc(flag)); 526 if (SLOT(label) == NULL) 527 return (ENOMEM); 528 529 return (0); 530 } 531 532 static void 533 biba_destroy_label(struct label *label) 534 { 535 536 biba_free(SLOT(label)); 537 SLOT_SET(label, NULL); 538 } 539 540 /* 541 * biba_element_to_string() accepts an sbuf and Biba element. It converts 542 * the Biba element to a string and stores the result in the sbuf; if there 543 * isn't space in the sbuf, -1 is returned. 544 */ 545 static int 546 biba_element_to_string(struct sbuf *sb, struct mac_biba_element *element) 547 { 548 int i, first; 549 550 switch (element->mbe_type) { 551 case MAC_BIBA_TYPE_HIGH: 552 return (sbuf_printf(sb, "high")); 553 554 case MAC_BIBA_TYPE_LOW: 555 return (sbuf_printf(sb, "low")); 556 557 case MAC_BIBA_TYPE_EQUAL: 558 return (sbuf_printf(sb, "equal")); 559 560 case MAC_BIBA_TYPE_GRADE: 561 if (sbuf_printf(sb, "%d", element->mbe_grade) == -1) 562 return (-1); 563 564 first = 1; 565 for (i = 1; i <= MAC_BIBA_MAX_COMPARTMENTS; i++) { 566 if (MAC_BIBA_BIT_TEST(i, element->mbe_compartments)) { 567 if (first) { 568 if (sbuf_putc(sb, ':') == -1) 569 return (-1); 570 if (sbuf_printf(sb, "%d", i) == -1) 571 return (-1); 572 first = 0; 573 } else { 574 if (sbuf_printf(sb, "+%d", i) == -1) 575 return (-1); 576 } 577 } 578 } 579 return (0); 580 581 default: 582 panic("biba_element_to_string: invalid type (%d)", 583 element->mbe_type); 584 } 585 } 586 587 /* 588 * biba_to_string() converts a Biba label to a string, and places the results 589 * in the passed sbuf. It returns 0 on success, or EINVAL if there isn't 590 * room in the sbuf. Note: the sbuf will be modified even in a failure case, 591 * so the caller may need to revert the sbuf by restoring the offset if 592 * that's undesired. 593 */ 594 static int 595 biba_to_string(struct sbuf *sb, struct mac_biba *mb) 596 { 597 598 if (mb->mb_flags & MAC_BIBA_FLAG_EFFECTIVE) { 599 if (biba_element_to_string(sb, &mb->mb_effective) == -1) 600 return (EINVAL); 601 } 602 603 if (mb->mb_flags & MAC_BIBA_FLAG_RANGE) { 604 if (sbuf_putc(sb, '(') == -1) 605 return (EINVAL); 606 607 if (biba_element_to_string(sb, &mb->mb_rangelow) == -1) 608 return (EINVAL); 609 610 if (sbuf_putc(sb, '-') == -1) 611 return (EINVAL); 612 613 if (biba_element_to_string(sb, &mb->mb_rangehigh) == -1) 614 return (EINVAL); 615 616 if (sbuf_putc(sb, ')') == -1) 617 return (EINVAL); 618 } 619 620 return (0); 621 } 622 623 static int 624 biba_externalize_label(struct label *label, char *element_name, 625 struct sbuf *sb, int *claimed) 626 { 627 struct mac_biba *mb; 628 629 if (strcmp(MAC_BIBA_LABEL_NAME, element_name) != 0) 630 return (0); 631 632 (*claimed)++; 633 634 mb = SLOT(label); 635 return (biba_to_string(sb, mb)); 636 } 637 638 static int 639 biba_parse_element(struct mac_biba_element *element, char *string) 640 { 641 char *compartment, *end, *grade; 642 int value; 643 644 if (strcmp(string, "high") == 0 || strcmp(string, "hi") == 0) { 645 element->mbe_type = MAC_BIBA_TYPE_HIGH; 646 element->mbe_grade = MAC_BIBA_TYPE_UNDEF; 647 } else if (strcmp(string, "low") == 0 || strcmp(string, "lo") == 0) { 648 element->mbe_type = MAC_BIBA_TYPE_LOW; 649 element->mbe_grade = MAC_BIBA_TYPE_UNDEF; 650 } else if (strcmp(string, "equal") == 0 || 651 strcmp(string, "eq") == 0) { 652 element->mbe_type = MAC_BIBA_TYPE_EQUAL; 653 element->mbe_grade = MAC_BIBA_TYPE_UNDEF; 654 } else { 655 element->mbe_type = MAC_BIBA_TYPE_GRADE; 656 657 /* 658 * Numeric grade piece of the element. 659 */ 660 grade = strsep(&string, ":"); 661 value = strtol(grade, &end, 10); 662 if (end == grade || *end != '\0') 663 return (EINVAL); 664 if (value < 0 || value > 65535) 665 return (EINVAL); 666 element->mbe_grade = value; 667 668 /* 669 * Optional compartment piece of the element. If none are 670 * included, we assume that the label has no compartments. 671 */ 672 if (string == NULL) 673 return (0); 674 if (*string == '\0') 675 return (0); 676 677 while ((compartment = strsep(&string, "+")) != NULL) { 678 value = strtol(compartment, &end, 10); 679 if (compartment == end || *end != '\0') 680 return (EINVAL); 681 if (value < 1 || value > MAC_BIBA_MAX_COMPARTMENTS) 682 return (EINVAL); 683 MAC_BIBA_BIT_SET(value, element->mbe_compartments); 684 } 685 } 686 687 return (0); 688 } 689 690 /* 691 * Note: destructively consumes the string, make a local copy before calling 692 * if that's a problem. 693 */ 694 static int 695 biba_parse(struct mac_biba *mb, char *string) 696 { 697 char *rangehigh, *rangelow, *effective; 698 int error; 699 700 effective = strsep(&string, "("); 701 if (*effective == '\0') 702 effective = NULL; 703 704 if (string != NULL) { 705 rangelow = strsep(&string, "-"); 706 if (string == NULL) 707 return (EINVAL); 708 rangehigh = strsep(&string, ")"); 709 if (string == NULL) 710 return (EINVAL); 711 if (*string != '\0') 712 return (EINVAL); 713 } else { 714 rangelow = NULL; 715 rangehigh = NULL; 716 } 717 718 KASSERT((rangelow != NULL && rangehigh != NULL) || 719 (rangelow == NULL && rangehigh == NULL), 720 ("biba_parse: range mismatch")); 721 722 bzero(mb, sizeof(*mb)); 723 if (effective != NULL) { 724 error = biba_parse_element(&mb->mb_effective, effective); 725 if (error) 726 return (error); 727 mb->mb_flags |= MAC_BIBA_FLAG_EFFECTIVE; 728 } 729 730 if (rangelow != NULL) { 731 error = biba_parse_element(&mb->mb_rangelow, rangelow); 732 if (error) 733 return (error); 734 error = biba_parse_element(&mb->mb_rangehigh, rangehigh); 735 if (error) 736 return (error); 737 mb->mb_flags |= MAC_BIBA_FLAG_RANGE; 738 } 739 740 error = biba_valid(mb); 741 if (error) 742 return (error); 743 744 return (0); 745 } 746 747 static int 748 biba_internalize_label(struct label *label, char *element_name, 749 char *element_data, int *claimed) 750 { 751 struct mac_biba *mb, mb_temp; 752 int error; 753 754 if (strcmp(MAC_BIBA_LABEL_NAME, element_name) != 0) 755 return (0); 756 757 (*claimed)++; 758 759 error = biba_parse(&mb_temp, element_data); 760 if (error) 761 return (error); 762 763 mb = SLOT(label); 764 *mb = mb_temp; 765 766 return (0); 767 } 768 769 static void 770 biba_copy_label(struct label *src, struct label *dest) 771 { 772 773 *SLOT(dest) = *SLOT(src); 774 } 775 776 /* 777 * Object-specific entry point implementations are sorted alphabetically by 778 * object type name and then by operation. 779 */ 780 static int 781 biba_bpfdesc_check_receive(struct bpf_d *d, struct label *dlabel, 782 struct ifnet *ifp, struct label *ifplabel) 783 { 784 struct mac_biba *a, *b; 785 786 if (!biba_enabled) 787 return (0); 788 789 a = SLOT(dlabel); 790 b = SLOT(ifplabel); 791 792 if (biba_equal_effective(a, b)) 793 return (0); 794 return (EACCES); 795 } 796 797 static void 798 biba_bpfdesc_create(struct ucred *cred, struct bpf_d *d, 799 struct label *dlabel) 800 { 801 struct mac_biba *source, *dest; 802 803 source = SLOT(cred->cr_label); 804 dest = SLOT(dlabel); 805 806 biba_copy_effective(source, dest); 807 } 808 809 static void 810 biba_bpfdesc_create_mbuf(struct bpf_d *d, struct label *dlabel, 811 struct mbuf *m, struct label *mlabel) 812 { 813 struct mac_biba *source, *dest; 814 815 source = SLOT(dlabel); 816 dest = SLOT(mlabel); 817 818 biba_copy_effective(source, dest); 819 } 820 821 static void 822 biba_cred_associate_nfsd(struct ucred *cred) 823 { 824 struct mac_biba *label; 825 826 label = SLOT(cred->cr_label); 827 biba_set_effective(label, MAC_BIBA_TYPE_LOW, 0, NULL); 828 biba_set_range(label, MAC_BIBA_TYPE_LOW, 0, NULL, MAC_BIBA_TYPE_HIGH, 829 0, NULL); 830 } 831 832 static int 833 biba_cred_check_relabel(struct ucred *cred, struct label *newlabel) 834 { 835 struct mac_biba *subj, *new; 836 int error; 837 838 subj = SLOT(cred->cr_label); 839 new = SLOT(newlabel); 840 841 /* 842 * If there is a Biba label update for the credential, it may 843 * be an update of the effective, range, or both. 844 */ 845 error = biba_atmostflags(new, MAC_BIBA_FLAGS_BOTH); 846 if (error) 847 return (error); 848 849 /* 850 * If the Biba label is to be changed, authorize as appropriate. 851 */ 852 if (new->mb_flags & MAC_BIBA_FLAGS_BOTH) { 853 /* 854 * If the change request modifies both the Biba label 855 * effective and range, check that the new effective will be 856 * in the new range. 857 */ 858 if ((new->mb_flags & MAC_BIBA_FLAGS_BOTH) == 859 MAC_BIBA_FLAGS_BOTH && 860 !biba_effective_in_range(new, new)) 861 return (EINVAL); 862 863 /* 864 * To change the Biba effective label on a credential, the 865 * new effective label must be in the current range. 866 */ 867 if (new->mb_flags & MAC_BIBA_FLAG_EFFECTIVE && 868 !biba_effective_in_range(new, subj)) 869 return (EPERM); 870 871 /* 872 * To change the Biba range on a credential, the new range 873 * label must be in the current range. 874 */ 875 if (new->mb_flags & MAC_BIBA_FLAG_RANGE && 876 !biba_range_in_range(new, subj)) 877 return (EPERM); 878 879 /* 880 * To have EQUAL in any component of the new credential Biba 881 * label, the subject must already have EQUAL in their label. 882 */ 883 if (biba_contains_equal(new)) { 884 error = biba_subject_privileged(subj); 885 if (error) 886 return (error); 887 } 888 } 889 890 return (0); 891 } 892 893 static int 894 biba_cred_check_visible(struct ucred *u1, struct ucred *u2) 895 { 896 struct mac_biba *subj, *obj; 897 898 if (!biba_enabled) 899 return (0); 900 901 subj = SLOT(u1->cr_label); 902 obj = SLOT(u2->cr_label); 903 904 /* XXX: range */ 905 if (!biba_dominate_effective(obj, subj)) 906 return (ESRCH); 907 908 return (0); 909 } 910 911 static void 912 biba_cred_create_init(struct ucred *cred) 913 { 914 struct mac_biba *dest; 915 916 dest = SLOT(cred->cr_label); 917 918 biba_set_effective(dest, MAC_BIBA_TYPE_HIGH, 0, NULL); 919 biba_set_range(dest, MAC_BIBA_TYPE_LOW, 0, NULL, MAC_BIBA_TYPE_HIGH, 920 0, NULL); 921 } 922 923 static void 924 biba_cred_create_swapper(struct ucred *cred) 925 { 926 struct mac_biba *dest; 927 928 dest = SLOT(cred->cr_label); 929 930 biba_set_effective(dest, MAC_BIBA_TYPE_EQUAL, 0, NULL); 931 biba_set_range(dest, MAC_BIBA_TYPE_LOW, 0, NULL, MAC_BIBA_TYPE_HIGH, 932 0, NULL); 933 } 934 935 static void 936 biba_cred_relabel(struct ucred *cred, struct label *newlabel) 937 { 938 struct mac_biba *source, *dest; 939 940 source = SLOT(newlabel); 941 dest = SLOT(cred->cr_label); 942 943 biba_copy(source, dest); 944 } 945 946 static void 947 biba_devfs_create_device(struct ucred *cred, struct mount *mp, 948 struct cdev *dev, struct devfs_dirent *de, struct label *delabel) 949 { 950 struct mac_biba *mb; 951 const char *dn; 952 int biba_type; 953 954 mb = SLOT(delabel); 955 dn = devtoname(dev); 956 if (strcmp(dn, "null") == 0 || 957 strcmp(dn, "zero") == 0 || 958 strcmp(dn, "random") == 0 || 959 strncmp(dn, "fd/", strlen("fd/")) == 0) 960 biba_type = MAC_BIBA_TYPE_EQUAL; 961 else if (ptys_equal && 962 (strncmp(dn, "ttyp", strlen("ttyp")) == 0 || 963 strncmp(dn, "pts/", strlen("pts/")) == 0 || 964 strncmp(dn, "ptyp", strlen("ptyp")) == 0)) 965 biba_type = MAC_BIBA_TYPE_EQUAL; 966 else 967 biba_type = MAC_BIBA_TYPE_HIGH; 968 biba_set_effective(mb, biba_type, 0, NULL); 969 } 970 971 static void 972 biba_devfs_create_directory(struct mount *mp, char *dirname, int dirnamelen, 973 struct devfs_dirent *de, struct label *delabel) 974 { 975 struct mac_biba *mb; 976 977 mb = SLOT(delabel); 978 979 biba_set_effective(mb, MAC_BIBA_TYPE_HIGH, 0, NULL); 980 } 981 982 static void 983 biba_devfs_create_symlink(struct ucred *cred, struct mount *mp, 984 struct devfs_dirent *dd, struct label *ddlabel, struct devfs_dirent *de, 985 struct label *delabel) 986 { 987 struct mac_biba *source, *dest; 988 989 source = SLOT(cred->cr_label); 990 dest = SLOT(delabel); 991 992 biba_copy_effective(source, dest); 993 } 994 995 static void 996 biba_devfs_update(struct mount *mp, struct devfs_dirent *de, 997 struct label *delabel, struct vnode *vp, struct label *vplabel) 998 { 999 struct mac_biba *source, *dest; 1000 1001 source = SLOT(vplabel); 1002 dest = SLOT(delabel); 1003 1004 biba_copy(source, dest); 1005 } 1006 1007 static void 1008 biba_devfs_vnode_associate(struct mount *mp, struct label *mntlabel, 1009 struct devfs_dirent *de, struct label *delabel, struct vnode *vp, 1010 struct label *vplabel) 1011 { 1012 struct mac_biba *source, *dest; 1013 1014 source = SLOT(delabel); 1015 dest = SLOT(vplabel); 1016 1017 biba_copy_effective(source, dest); 1018 } 1019 1020 static int 1021 biba_ifnet_check_relabel(struct ucred *cred, struct ifnet *ifp, 1022 struct label *ifplabel, struct label *newlabel) 1023 { 1024 struct mac_biba *subj, *new; 1025 int error; 1026 1027 subj = SLOT(cred->cr_label); 1028 new = SLOT(newlabel); 1029 1030 /* 1031 * If there is a Biba label update for the interface, it may be an 1032 * update of the effective, range, or both. 1033 */ 1034 error = biba_atmostflags(new, MAC_BIBA_FLAGS_BOTH); 1035 if (error) 1036 return (error); 1037 1038 /* 1039 * Relabling network interfaces requires Biba privilege. 1040 */ 1041 error = biba_subject_privileged(subj); 1042 if (error) 1043 return (error); 1044 1045 return (0); 1046 } 1047 1048 static int 1049 biba_ifnet_check_transmit(struct ifnet *ifp, struct label *ifplabel, 1050 struct mbuf *m, struct label *mlabel) 1051 { 1052 struct mac_biba *p, *i; 1053 1054 if (!biba_enabled) 1055 return (0); 1056 1057 p = SLOT(mlabel); 1058 i = SLOT(ifplabel); 1059 1060 return (biba_effective_in_range(p, i) ? 0 : EACCES); 1061 } 1062 1063 static void 1064 biba_ifnet_create(struct ifnet *ifp, struct label *ifplabel) 1065 { 1066 char tifname[IFNAMSIZ], *p, *q; 1067 char tiflist[sizeof(trusted_interfaces)]; 1068 struct mac_biba *dest; 1069 int len, type; 1070 1071 dest = SLOT(ifplabel); 1072 1073 if (ifp->if_type == IFT_LOOP || interfaces_equal != 0) { 1074 type = MAC_BIBA_TYPE_EQUAL; 1075 goto set; 1076 } 1077 1078 if (trust_all_interfaces) { 1079 type = MAC_BIBA_TYPE_HIGH; 1080 goto set; 1081 } 1082 1083 type = MAC_BIBA_TYPE_LOW; 1084 1085 if (trusted_interfaces[0] == '\0' || 1086 !strvalid(trusted_interfaces, sizeof(trusted_interfaces))) 1087 goto set; 1088 1089 bzero(tiflist, sizeof(tiflist)); 1090 for (p = trusted_interfaces, q = tiflist; *p != '\0'; p++, q++) 1091 if(*p != ' ' && *p != '\t') 1092 *q = *p; 1093 1094 for (p = q = tiflist;; p++) { 1095 if (*p == ',' || *p == '\0') { 1096 len = p - q; 1097 if (len < IFNAMSIZ) { 1098 bzero(tifname, sizeof(tifname)); 1099 bcopy(q, tifname, len); 1100 if (strcmp(tifname, ifp->if_xname) == 0) { 1101 type = MAC_BIBA_TYPE_HIGH; 1102 break; 1103 } 1104 } else { 1105 *p = '\0'; 1106 printf("mac_biba warning: interface name " 1107 "\"%s\" is too long (must be < %d)\n", 1108 q, IFNAMSIZ); 1109 } 1110 if (*p == '\0') 1111 break; 1112 q = p + 1; 1113 } 1114 } 1115 set: 1116 biba_set_effective(dest, type, 0, NULL); 1117 biba_set_range(dest, type, 0, NULL, type, 0, NULL); 1118 } 1119 1120 static void 1121 biba_ifnet_create_mbuf(struct ifnet *ifp, struct label *ifplabel, 1122 struct mbuf *m, struct label *mlabel) 1123 { 1124 struct mac_biba *source, *dest; 1125 1126 source = SLOT(ifplabel); 1127 dest = SLOT(mlabel); 1128 1129 biba_copy_effective(source, dest); 1130 } 1131 1132 static void 1133 biba_ifnet_relabel(struct ucred *cred, struct ifnet *ifp, 1134 struct label *ifplabel, struct label *newlabel) 1135 { 1136 struct mac_biba *source, *dest; 1137 1138 source = SLOT(newlabel); 1139 dest = SLOT(ifplabel); 1140 1141 biba_copy(source, dest); 1142 } 1143 1144 static int 1145 biba_inpcb_check_deliver(struct inpcb *inp, struct label *inplabel, 1146 struct mbuf *m, struct label *mlabel) 1147 { 1148 struct mac_biba *p, *i; 1149 1150 if (!biba_enabled) 1151 return (0); 1152 1153 p = SLOT(mlabel); 1154 i = SLOT(inplabel); 1155 1156 return (biba_equal_effective(p, i) ? 0 : EACCES); 1157 } 1158 1159 static int 1160 biba_inpcb_check_visible(struct ucred *cred, struct inpcb *inp, 1161 struct label *inplabel) 1162 { 1163 struct mac_biba *subj, *obj; 1164 1165 if (!biba_enabled) 1166 return (0); 1167 1168 subj = SLOT(cred->cr_label); 1169 obj = SLOT(inplabel); 1170 1171 if (!biba_dominate_effective(obj, subj)) 1172 return (ENOENT); 1173 1174 return (0); 1175 } 1176 1177 static void 1178 biba_inpcb_create(struct socket *so, struct label *solabel, 1179 struct inpcb *inp, struct label *inplabel) 1180 { 1181 struct mac_biba *source, *dest; 1182 1183 source = SLOT(solabel); 1184 dest = SLOT(inplabel); 1185 1186 SOCK_LOCK(so); 1187 biba_copy_effective(source, dest); 1188 SOCK_UNLOCK(so); 1189 } 1190 1191 static void 1192 biba_inpcb_create_mbuf(struct inpcb *inp, struct label *inplabel, 1193 struct mbuf *m, struct label *mlabel) 1194 { 1195 struct mac_biba *source, *dest; 1196 1197 source = SLOT(inplabel); 1198 dest = SLOT(mlabel); 1199 1200 biba_copy_effective(source, dest); 1201 } 1202 1203 static void 1204 biba_inpcb_sosetlabel(struct socket *so, struct label *solabel, 1205 struct inpcb *inp, struct label *inplabel) 1206 { 1207 struct mac_biba *source, *dest; 1208 1209 SOCK_LOCK_ASSERT(so); 1210 1211 source = SLOT(solabel); 1212 dest = SLOT(inplabel); 1213 1214 biba_copy(source, dest); 1215 } 1216 1217 static void 1218 biba_ip6q_create(struct mbuf *m, struct label *mlabel, struct ip6q *q6, 1219 struct label *q6label) 1220 { 1221 struct mac_biba *source, *dest; 1222 1223 source = SLOT(mlabel); 1224 dest = SLOT(q6label); 1225 1226 biba_copy_effective(source, dest); 1227 } 1228 1229 static int 1230 biba_ip6q_match(struct mbuf *m, struct label *mlabel, struct ip6q *q6, 1231 struct label *q6label) 1232 { 1233 struct mac_biba *a, *b; 1234 1235 a = SLOT(q6label); 1236 b = SLOT(mlabel); 1237 1238 return (biba_equal_effective(a, b)); 1239 } 1240 1241 static void 1242 biba_ip6q_reassemble(struct ip6q *q6, struct label *q6label, struct mbuf *m, 1243 struct label *mlabel) 1244 { 1245 struct mac_biba *source, *dest; 1246 1247 source = SLOT(q6label); 1248 dest = SLOT(mlabel); 1249 1250 /* Just use the head, since we require them all to match. */ 1251 biba_copy_effective(source, dest); 1252 } 1253 1254 static void 1255 biba_ip6q_update(struct mbuf *m, struct label *mlabel, struct ip6q *q6, 1256 struct label *q6label) 1257 { 1258 1259 /* NOOP: we only accept matching labels, so no need to update */ 1260 } 1261 1262 static void 1263 biba_ipq_create(struct mbuf *m, struct label *mlabel, struct ipq *q, 1264 struct label *qlabel) 1265 { 1266 struct mac_biba *source, *dest; 1267 1268 source = SLOT(mlabel); 1269 dest = SLOT(qlabel); 1270 1271 biba_copy_effective(source, dest); 1272 } 1273 1274 static int 1275 biba_ipq_match(struct mbuf *m, struct label *mlabel, struct ipq *q, 1276 struct label *qlabel) 1277 { 1278 struct mac_biba *a, *b; 1279 1280 a = SLOT(qlabel); 1281 b = SLOT(mlabel); 1282 1283 return (biba_equal_effective(a, b)); 1284 } 1285 1286 static void 1287 biba_ipq_reassemble(struct ipq *q, struct label *qlabel, struct mbuf *m, 1288 struct label *mlabel) 1289 { 1290 struct mac_biba *source, *dest; 1291 1292 source = SLOT(qlabel); 1293 dest = SLOT(mlabel); 1294 1295 /* Just use the head, since we require them all to match. */ 1296 biba_copy_effective(source, dest); 1297 } 1298 1299 static void 1300 biba_ipq_update(struct mbuf *m, struct label *mlabel, struct ipq *q, 1301 struct label *qlabel) 1302 { 1303 1304 /* NOOP: we only accept matching labels, so no need to update */ 1305 } 1306 1307 static int 1308 biba_kld_check_load(struct ucred *cred, struct vnode *vp, 1309 struct label *vplabel) 1310 { 1311 struct mac_biba *subj, *obj; 1312 int error; 1313 1314 if (!biba_enabled) 1315 return (0); 1316 1317 subj = SLOT(cred->cr_label); 1318 1319 error = biba_subject_privileged(subj); 1320 if (error) 1321 return (error); 1322 1323 obj = SLOT(vplabel); 1324 if (!biba_high_effective(obj)) 1325 return (EACCES); 1326 1327 return (0); 1328 } 1329 1330 static int 1331 biba_mount_check_stat(struct ucred *cred, struct mount *mp, 1332 struct label *mplabel) 1333 { 1334 struct mac_biba *subj, *obj; 1335 1336 if (!biba_enabled) 1337 return (0); 1338 1339 subj = SLOT(cred->cr_label); 1340 obj = SLOT(mplabel); 1341 1342 if (!biba_dominate_effective(obj, subj)) 1343 return (EACCES); 1344 1345 return (0); 1346 } 1347 1348 static void 1349 biba_mount_create(struct ucred *cred, struct mount *mp, 1350 struct label *mplabel) 1351 { 1352 struct mac_biba *source, *dest; 1353 1354 source = SLOT(cred->cr_label); 1355 dest = SLOT(mplabel); 1356 1357 biba_copy_effective(source, dest); 1358 } 1359 1360 static void 1361 biba_netatalk_aarp_send(struct ifnet *ifp, struct label *ifplabel, 1362 struct mbuf *m, struct label *mlabel) 1363 { 1364 struct mac_biba *dest; 1365 1366 dest = SLOT(mlabel); 1367 1368 biba_set_effective(dest, MAC_BIBA_TYPE_EQUAL, 0, NULL); 1369 } 1370 1371 static void 1372 biba_netinet_arp_send(struct ifnet *ifp, struct label *ifplabel, 1373 struct mbuf *m, struct label *mlabel) 1374 { 1375 struct mac_biba *dest; 1376 1377 dest = SLOT(mlabel); 1378 1379 biba_set_effective(dest, MAC_BIBA_TYPE_EQUAL, 0, NULL); 1380 } 1381 1382 static void 1383 biba_netinet_firewall_reply(struct mbuf *mrecv, struct label *mrecvlabel, 1384 struct mbuf *msend, struct label *msendlabel) 1385 { 1386 struct mac_biba *source, *dest; 1387 1388 source = SLOT(mrecvlabel); 1389 dest = SLOT(msendlabel); 1390 1391 biba_copy_effective(source, dest); 1392 } 1393 1394 static void 1395 biba_netinet_firewall_send(struct mbuf *m, struct label *mlabel) 1396 { 1397 struct mac_biba *dest; 1398 1399 dest = SLOT(mlabel); 1400 1401 /* XXX: where is the label for the firewall really coming from? */ 1402 biba_set_effective(dest, MAC_BIBA_TYPE_EQUAL, 0, NULL); 1403 } 1404 1405 static void 1406 biba_netinet_fragment(struct mbuf *m, struct label *mlabel, 1407 struct mbuf *frag, struct label *fraglabel) 1408 { 1409 struct mac_biba *source, *dest; 1410 1411 source = SLOT(mlabel); 1412 dest = SLOT(fraglabel); 1413 1414 biba_copy_effective(source, dest); 1415 } 1416 1417 static void 1418 biba_netinet_icmp_reply(struct mbuf *mrecv, struct label *mrecvlabel, 1419 struct mbuf *msend, struct label *msendlabel) 1420 { 1421 struct mac_biba *source, *dest; 1422 1423 source = SLOT(mrecvlabel); 1424 dest = SLOT(msendlabel); 1425 1426 biba_copy_effective(source, dest); 1427 } 1428 1429 static void 1430 biba_netinet_igmp_send(struct ifnet *ifp, struct label *ifplabel, 1431 struct mbuf *m, struct label *mlabel) 1432 { 1433 struct mac_biba *dest; 1434 1435 dest = SLOT(mlabel); 1436 1437 biba_set_effective(dest, MAC_BIBA_TYPE_EQUAL, 0, NULL); 1438 } 1439 1440 static void 1441 biba_netinet6_nd6_send(struct ifnet *ifp, struct label *ifplabel, 1442 struct mbuf *m, struct label *mlabel) 1443 { 1444 struct mac_biba *dest; 1445 1446 dest = SLOT(mlabel); 1447 1448 biba_set_effective(dest, MAC_BIBA_TYPE_EQUAL, 0, NULL); 1449 } 1450 1451 static int 1452 biba_pipe_check_ioctl(struct ucred *cred, struct pipepair *pp, 1453 struct label *pplabel, unsigned long cmd, void /* caddr_t */ *data) 1454 { 1455 1456 if(!biba_enabled) 1457 return (0); 1458 1459 /* XXX: This will be implemented soon... */ 1460 1461 return (0); 1462 } 1463 1464 static int 1465 biba_pipe_check_poll(struct ucred *cred, struct pipepair *pp, 1466 struct label *pplabel) 1467 { 1468 struct mac_biba *subj, *obj; 1469 1470 if (!biba_enabled) 1471 return (0); 1472 1473 subj = SLOT(cred->cr_label); 1474 obj = SLOT(pplabel); 1475 1476 if (!biba_dominate_effective(obj, subj)) 1477 return (EACCES); 1478 1479 return (0); 1480 } 1481 1482 static int 1483 biba_pipe_check_read(struct ucred *cred, struct pipepair *pp, 1484 struct label *pplabel) 1485 { 1486 struct mac_biba *subj, *obj; 1487 1488 if (!biba_enabled) 1489 return (0); 1490 1491 subj = SLOT(cred->cr_label); 1492 obj = SLOT(pplabel); 1493 1494 if (!biba_dominate_effective(obj, subj)) 1495 return (EACCES); 1496 1497 return (0); 1498 } 1499 1500 static int 1501 biba_pipe_check_relabel(struct ucred *cred, struct pipepair *pp, 1502 struct label *pplabel, struct label *newlabel) 1503 { 1504 struct mac_biba *subj, *obj, *new; 1505 int error; 1506 1507 new = SLOT(newlabel); 1508 subj = SLOT(cred->cr_label); 1509 obj = SLOT(pplabel); 1510 1511 /* 1512 * If there is a Biba label update for a pipe, it must be a effective 1513 * update. 1514 */ 1515 error = biba_atmostflags(new, MAC_BIBA_FLAG_EFFECTIVE); 1516 if (error) 1517 return (error); 1518 1519 /* 1520 * To perform a relabel of a pipe (Biba label or not), Biba must 1521 * authorize the relabel. 1522 */ 1523 if (!biba_effective_in_range(obj, subj)) 1524 return (EPERM); 1525 1526 /* 1527 * If the Biba label is to be changed, authorize as appropriate. 1528 */ 1529 if (new->mb_flags & MAC_BIBA_FLAG_EFFECTIVE) { 1530 /* 1531 * To change the Biba label on a pipe, the new pipe label 1532 * must be in the subject range. 1533 */ 1534 if (!biba_effective_in_range(new, subj)) 1535 return (EPERM); 1536 1537 /* 1538 * To change the Biba label on a pipe to be EQUAL, the 1539 * subject must have appropriate privilege. 1540 */ 1541 if (biba_contains_equal(new)) { 1542 error = biba_subject_privileged(subj); 1543 if (error) 1544 return (error); 1545 } 1546 } 1547 1548 return (0); 1549 } 1550 1551 static int 1552 biba_pipe_check_stat(struct ucred *cred, struct pipepair *pp, 1553 struct label *pplabel) 1554 { 1555 struct mac_biba *subj, *obj; 1556 1557 if (!biba_enabled) 1558 return (0); 1559 1560 subj = SLOT(cred->cr_label); 1561 obj = SLOT(pplabel); 1562 1563 if (!biba_dominate_effective(obj, subj)) 1564 return (EACCES); 1565 1566 return (0); 1567 } 1568 1569 static int 1570 biba_pipe_check_write(struct ucred *cred, struct pipepair *pp, 1571 struct label *pplabel) 1572 { 1573 struct mac_biba *subj, *obj; 1574 1575 if (!biba_enabled) 1576 return (0); 1577 1578 subj = SLOT(cred->cr_label); 1579 obj = SLOT(pplabel); 1580 1581 if (!biba_dominate_effective(subj, obj)) 1582 return (EACCES); 1583 1584 return (0); 1585 } 1586 1587 static void 1588 biba_pipe_create(struct ucred *cred, struct pipepair *pp, 1589 struct label *pplabel) 1590 { 1591 struct mac_biba *source, *dest; 1592 1593 source = SLOT(cred->cr_label); 1594 dest = SLOT(pplabel); 1595 1596 biba_copy_effective(source, dest); 1597 } 1598 1599 static void 1600 biba_pipe_relabel(struct ucred *cred, struct pipepair *pp, 1601 struct label *pplabel, struct label *newlabel) 1602 { 1603 struct mac_biba *source, *dest; 1604 1605 source = SLOT(newlabel); 1606 dest = SLOT(pplabel); 1607 1608 biba_copy(source, dest); 1609 } 1610 1611 static int 1612 biba_posixsem_check_openunlink(struct ucred *cred, struct ksem *ks, 1613 struct label *kslabel) 1614 { 1615 struct mac_biba *subj, *obj; 1616 1617 if (!biba_enabled) 1618 return (0); 1619 1620 subj = SLOT(cred->cr_label); 1621 obj = SLOT(kslabel); 1622 1623 if (!biba_dominate_effective(subj, obj)) 1624 return (EACCES); 1625 1626 return (0); 1627 } 1628 1629 static int 1630 biba_posixsem_check_setmode(struct ucred *cred, struct ksem *ks, 1631 struct label *kslabel, mode_t mode) 1632 { 1633 struct mac_biba *subj, *obj; 1634 1635 if (!biba_enabled) 1636 return (0); 1637 1638 subj = SLOT(cred->cr_label); 1639 obj = SLOT(kslabel); 1640 1641 if (!biba_dominate_effective(subj, obj)) 1642 return (EACCES); 1643 1644 return (0); 1645 } 1646 1647 static int 1648 biba_posixsem_check_setowner(struct ucred *cred, struct ksem *ks, 1649 struct label *kslabel, uid_t uid, gid_t gid) 1650 { 1651 struct mac_biba *subj, *obj; 1652 1653 if (!biba_enabled) 1654 return (0); 1655 1656 subj = SLOT(cred->cr_label); 1657 obj = SLOT(kslabel); 1658 1659 if (!biba_dominate_effective(subj, obj)) 1660 return (EACCES); 1661 1662 return (0); 1663 } 1664 1665 static int 1666 biba_posixsem_check_write(struct ucred *active_cred, struct ucred *file_cred, 1667 struct ksem *ks, struct label *kslabel) 1668 { 1669 struct mac_biba *subj, *obj; 1670 1671 if (!biba_enabled) 1672 return (0); 1673 1674 subj = SLOT(active_cred->cr_label); 1675 obj = SLOT(kslabel); 1676 1677 if (!biba_dominate_effective(subj, obj)) 1678 return (EACCES); 1679 1680 return (0); 1681 } 1682 1683 static int 1684 biba_posixsem_check_rdonly(struct ucred *active_cred, struct ucred *file_cred, 1685 struct ksem *ks, struct label *kslabel) 1686 { 1687 struct mac_biba *subj, *obj; 1688 1689 if (!biba_enabled) 1690 return (0); 1691 1692 subj = SLOT(active_cred->cr_label); 1693 obj = SLOT(kslabel); 1694 1695 if (!biba_dominate_effective(obj, subj)) 1696 return (EACCES); 1697 1698 return (0); 1699 } 1700 1701 static void 1702 biba_posixsem_create(struct ucred *cred, struct ksem *ks, 1703 struct label *kslabel) 1704 { 1705 struct mac_biba *source, *dest; 1706 1707 source = SLOT(cred->cr_label); 1708 dest = SLOT(kslabel); 1709 1710 biba_copy_effective(source, dest); 1711 } 1712 1713 static int 1714 biba_posixshm_check_mmap(struct ucred *cred, struct shmfd *shmfd, 1715 struct label *shmlabel, int prot, int flags) 1716 { 1717 struct mac_biba *subj, *obj; 1718 1719 if (!biba_enabled || !revocation_enabled) 1720 return (0); 1721 1722 subj = SLOT(cred->cr_label); 1723 obj = SLOT(shmlabel); 1724 1725 if (prot & (VM_PROT_READ | VM_PROT_EXECUTE)) { 1726 if (!biba_dominate_effective(obj, subj)) 1727 return (EACCES); 1728 } 1729 if (((prot & VM_PROT_WRITE) != 0) && ((flags & MAP_SHARED) != 0)) { 1730 if (!biba_dominate_effective(subj, obj)) 1731 return (EACCES); 1732 } 1733 1734 return (0); 1735 } 1736 1737 static int 1738 biba_posixshm_check_open(struct ucred *cred, struct shmfd *shmfd, 1739 struct label *shmlabel, accmode_t accmode) 1740 { 1741 struct mac_biba *subj, *obj; 1742 1743 if (!biba_enabled) 1744 return (0); 1745 1746 subj = SLOT(cred->cr_label); 1747 obj = SLOT(shmlabel); 1748 1749 if (accmode & (VREAD | VEXEC | VSTAT_PERMS)) { 1750 if (!biba_dominate_effective(obj, subj)) 1751 return (EACCES); 1752 } 1753 if (accmode & VMODIFY_PERMS) { 1754 if (!biba_dominate_effective(subj, obj)) 1755 return (EACCES); 1756 } 1757 1758 return (0); 1759 } 1760 1761 static int 1762 biba_posixshm_check_read(struct ucred *active_cred, struct ucred *file_cred, 1763 struct shmfd *vp, struct label *shmlabel) 1764 { 1765 struct mac_biba *subj, *obj; 1766 1767 if (!biba_enabled || !revocation_enabled) 1768 return (0); 1769 1770 subj = SLOT(active_cred->cr_label); 1771 obj = SLOT(shmlabel); 1772 1773 if (!biba_dominate_effective(obj, subj)) 1774 return (EACCES); 1775 1776 return (0); 1777 } 1778 1779 static int 1780 biba_posixshm_check_setmode(struct ucred *cred, struct shmfd *shmfd, 1781 struct label *shmlabel, mode_t mode) 1782 { 1783 struct mac_biba *subj, *obj; 1784 1785 if (!biba_enabled) 1786 return (0); 1787 1788 subj = SLOT(cred->cr_label); 1789 obj = SLOT(shmlabel); 1790 1791 if (!biba_dominate_effective(subj, obj)) 1792 return (EACCES); 1793 1794 return (0); 1795 } 1796 1797 static int 1798 biba_posixshm_check_setowner(struct ucred *cred, struct shmfd *shmfd, 1799 struct label *shmlabel, uid_t uid, gid_t gid) 1800 { 1801 struct mac_biba *subj, *obj; 1802 1803 if (!biba_enabled) 1804 return (0); 1805 1806 subj = SLOT(cred->cr_label); 1807 obj = SLOT(shmlabel); 1808 1809 if (!biba_dominate_effective(subj, obj)) 1810 return (EACCES); 1811 1812 return (0); 1813 } 1814 1815 static int 1816 biba_posixshm_check_stat(struct ucred *active_cred, struct ucred *file_cred, 1817 struct shmfd *shmfd, struct label *shmlabel) 1818 { 1819 struct mac_biba *subj, *obj; 1820 1821 if (!biba_enabled) 1822 return (0); 1823 1824 subj = SLOT(active_cred->cr_label); 1825 obj = SLOT(shmlabel); 1826 1827 if (!biba_dominate_effective(obj, subj)) 1828 return (EACCES); 1829 1830 return (0); 1831 } 1832 1833 static int 1834 biba_posixshm_check_truncate(struct ucred *active_cred, 1835 struct ucred *file_cred, struct shmfd *shmfd, struct label *shmlabel) 1836 { 1837 struct mac_biba *subj, *obj; 1838 1839 if (!biba_enabled) 1840 return (0); 1841 1842 subj = SLOT(active_cred->cr_label); 1843 obj = SLOT(shmlabel); 1844 1845 if (!biba_dominate_effective(subj, obj)) 1846 return (EACCES); 1847 1848 return (0); 1849 } 1850 1851 static int 1852 biba_posixshm_check_unlink(struct ucred *cred, struct shmfd *shmfd, 1853 struct label *shmlabel) 1854 { 1855 struct mac_biba *subj, *obj; 1856 1857 if (!biba_enabled) 1858 return (0); 1859 1860 subj = SLOT(cred->cr_label); 1861 obj = SLOT(shmlabel); 1862 1863 if (!biba_dominate_effective(subj, obj)) 1864 return (EACCES); 1865 1866 return (0); 1867 } 1868 1869 static int 1870 biba_posixshm_check_write(struct ucred *active_cred, struct ucred *file_cred, 1871 struct shmfd *vp, struct label *shmlabel) 1872 { 1873 struct mac_biba *subj, *obj; 1874 1875 if (!biba_enabled || !revocation_enabled) 1876 return (0); 1877 1878 subj = SLOT(active_cred->cr_label); 1879 obj = SLOT(shmlabel); 1880 1881 if (!biba_dominate_effective(obj, subj)) 1882 return (EACCES); 1883 1884 return (0); 1885 } 1886 1887 static void 1888 biba_posixshm_create(struct ucred *cred, struct shmfd *shmfd, 1889 struct label *shmlabel) 1890 { 1891 struct mac_biba *source, *dest; 1892 1893 source = SLOT(cred->cr_label); 1894 dest = SLOT(shmlabel); 1895 1896 biba_copy_effective(source, dest); 1897 } 1898 1899 /* 1900 * Some system privileges are allowed regardless of integrity grade; others 1901 * are allowed only when running with privilege with respect to the Biba 1902 * policy as they might otherwise allow bypassing of the integrity policy. 1903 */ 1904 static int 1905 biba_priv_check(struct ucred *cred, int priv) 1906 { 1907 struct mac_biba *subj; 1908 int error; 1909 1910 if (!biba_enabled) 1911 return (0); 1912 1913 /* 1914 * Exempt only specific privileges from the Biba integrity policy. 1915 */ 1916 switch (priv) { 1917 case PRIV_KTRACE: 1918 case PRIV_MSGBUF: 1919 1920 /* 1921 * Allow processes to manipulate basic process audit properties, and 1922 * to submit audit records. 1923 */ 1924 case PRIV_AUDIT_GETAUDIT: 1925 case PRIV_AUDIT_SETAUDIT: 1926 case PRIV_AUDIT_SUBMIT: 1927 1928 /* 1929 * Allow processes to manipulate their regular UNIX credentials. 1930 */ 1931 case PRIV_CRED_SETUID: 1932 case PRIV_CRED_SETEUID: 1933 case PRIV_CRED_SETGID: 1934 case PRIV_CRED_SETEGID: 1935 case PRIV_CRED_SETGROUPS: 1936 case PRIV_CRED_SETREUID: 1937 case PRIV_CRED_SETREGID: 1938 case PRIV_CRED_SETRESUID: 1939 case PRIV_CRED_SETRESGID: 1940 1941 /* 1942 * Allow processes to perform system monitoring. 1943 */ 1944 case PRIV_SEEOTHERGIDS: 1945 case PRIV_SEEOTHERUIDS: 1946 break; 1947 1948 /* 1949 * Allow access to general process debugging facilities. We 1950 * separately control debugging based on MAC label. 1951 */ 1952 case PRIV_DEBUG_DIFFCRED: 1953 case PRIV_DEBUG_SUGID: 1954 case PRIV_DEBUG_UNPRIV: 1955 1956 /* 1957 * Allow manipulating jails. 1958 */ 1959 case PRIV_JAIL_ATTACH: 1960 1961 /* 1962 * Allow privilege with respect to the Partition policy, but not the 1963 * Privs policy. 1964 */ 1965 case PRIV_MAC_PARTITION: 1966 1967 /* 1968 * Allow privilege with respect to process resource limits and login 1969 * context. 1970 */ 1971 case PRIV_PROC_LIMIT: 1972 case PRIV_PROC_SETLOGIN: 1973 case PRIV_PROC_SETRLIMIT: 1974 1975 /* 1976 * Allow System V and POSIX IPC privileges. 1977 */ 1978 case PRIV_IPC_READ: 1979 case PRIV_IPC_WRITE: 1980 case PRIV_IPC_ADMIN: 1981 case PRIV_IPC_MSGSIZE: 1982 case PRIV_MQ_ADMIN: 1983 1984 /* 1985 * Allow certain scheduler manipulations -- possibly this should be 1986 * controlled by more fine-grained policy, as potentially low 1987 * integrity processes can deny CPU to higher integrity ones. 1988 */ 1989 case PRIV_SCHED_DIFFCRED: 1990 case PRIV_SCHED_SETPRIORITY: 1991 case PRIV_SCHED_RTPRIO: 1992 case PRIV_SCHED_SETPOLICY: 1993 case PRIV_SCHED_SET: 1994 case PRIV_SCHED_SETPARAM: 1995 1996 /* 1997 * More IPC privileges. 1998 */ 1999 case PRIV_SEM_WRITE: 2000 2001 /* 2002 * Allow signaling privileges subject to integrity policy. 2003 */ 2004 case PRIV_SIGNAL_DIFFCRED: 2005 case PRIV_SIGNAL_SUGID: 2006 2007 /* 2008 * Allow access to only limited sysctls from lower integrity levels; 2009 * piggy-back on the Jail definition. 2010 */ 2011 case PRIV_SYSCTL_WRITEJAIL: 2012 2013 /* 2014 * Allow TTY-based privileges, subject to general device access using 2015 * labels on TTY device nodes, but not console privilege. 2016 */ 2017 case PRIV_TTY_DRAINWAIT: 2018 case PRIV_TTY_DTRWAIT: 2019 case PRIV_TTY_EXCLUSIVE: 2020 case PRIV_TTY_STI: 2021 case PRIV_TTY_SETA: 2022 2023 /* 2024 * Grant most VFS privileges, as almost all are in practice bounded 2025 * by more specific checks using labels. 2026 */ 2027 case PRIV_VFS_READ: 2028 case PRIV_VFS_WRITE: 2029 case PRIV_VFS_ADMIN: 2030 case PRIV_VFS_EXEC: 2031 case PRIV_VFS_LOOKUP: 2032 case PRIV_VFS_CHFLAGS_DEV: 2033 case PRIV_VFS_CHOWN: 2034 case PRIV_VFS_CHROOT: 2035 case PRIV_VFS_RETAINSUGID: 2036 case PRIV_VFS_EXCEEDQUOTA: 2037 case PRIV_VFS_FCHROOT: 2038 case PRIV_VFS_FHOPEN: 2039 case PRIV_VFS_FHSTATFS: 2040 case PRIV_VFS_GENERATION: 2041 case PRIV_VFS_GETFH: 2042 case PRIV_VFS_GETQUOTA: 2043 case PRIV_VFS_LINK: 2044 case PRIV_VFS_MOUNT: 2045 case PRIV_VFS_MOUNT_OWNER: 2046 case PRIV_VFS_MOUNT_PERM: 2047 case PRIV_VFS_MOUNT_SUIDDIR: 2048 case PRIV_VFS_MOUNT_NONUSER: 2049 case PRIV_VFS_SETGID: 2050 case PRIV_VFS_STICKYFILE: 2051 case PRIV_VFS_SYSFLAGS: 2052 case PRIV_VFS_UNMOUNT: 2053 2054 /* 2055 * Allow VM privileges; it would be nice if these were subject to 2056 * resource limits. 2057 */ 2058 case PRIV_VM_MADV_PROTECT: 2059 case PRIV_VM_MLOCK: 2060 case PRIV_VM_MUNLOCK: 2061 case PRIV_VM_SWAP_NOQUOTA: 2062 case PRIV_VM_SWAP_NORLIMIT: 2063 2064 /* 2065 * Allow some but not all network privileges. In general, dont allow 2066 * reconfiguring the network stack, just normal use. 2067 */ 2068 case PRIV_NETATALK_RESERVEDPORT: 2069 case PRIV_NETINET_RESERVEDPORT: 2070 case PRIV_NETINET_RAW: 2071 case PRIV_NETINET_REUSEPORT: 2072 break; 2073 2074 /* 2075 * All remaining system privileges are allow only if the process 2076 * holds privilege with respect to the Biba policy. 2077 */ 2078 default: 2079 subj = SLOT(cred->cr_label); 2080 error = biba_subject_privileged(subj); 2081 if (error) 2082 return (error); 2083 } 2084 return (0); 2085 } 2086 2087 static int 2088 biba_proc_check_debug(struct ucred *cred, struct proc *p) 2089 { 2090 struct mac_biba *subj, *obj; 2091 2092 if (!biba_enabled) 2093 return (0); 2094 2095 subj = SLOT(cred->cr_label); 2096 obj = SLOT(p->p_ucred->cr_label); 2097 2098 /* XXX: range checks */ 2099 if (!biba_dominate_effective(obj, subj)) 2100 return (ESRCH); 2101 if (!biba_dominate_effective(subj, obj)) 2102 return (EACCES); 2103 2104 return (0); 2105 } 2106 2107 static int 2108 biba_proc_check_sched(struct ucred *cred, struct proc *p) 2109 { 2110 struct mac_biba *subj, *obj; 2111 2112 if (!biba_enabled) 2113 return (0); 2114 2115 subj = SLOT(cred->cr_label); 2116 obj = SLOT(p->p_ucred->cr_label); 2117 2118 /* XXX: range checks */ 2119 if (!biba_dominate_effective(obj, subj)) 2120 return (ESRCH); 2121 if (!biba_dominate_effective(subj, obj)) 2122 return (EACCES); 2123 2124 return (0); 2125 } 2126 2127 static int 2128 biba_proc_check_signal(struct ucred *cred, struct proc *p, int signum) 2129 { 2130 struct mac_biba *subj, *obj; 2131 2132 if (!biba_enabled) 2133 return (0); 2134 2135 subj = SLOT(cred->cr_label); 2136 obj = SLOT(p->p_ucred->cr_label); 2137 2138 /* XXX: range checks */ 2139 if (!biba_dominate_effective(obj, subj)) 2140 return (ESRCH); 2141 if (!biba_dominate_effective(subj, obj)) 2142 return (EACCES); 2143 2144 return (0); 2145 } 2146 2147 static int 2148 biba_socket_check_deliver(struct socket *so, struct label *solabel, 2149 struct mbuf *m, struct label *mlabel) 2150 { 2151 struct mac_biba *p, *s; 2152 int error; 2153 2154 if (!biba_enabled) 2155 return (0); 2156 2157 p = SLOT(mlabel); 2158 s = SLOT(solabel); 2159 2160 SOCK_LOCK(so); 2161 error = biba_equal_effective(p, s) ? 0 : EACCES; 2162 SOCK_UNLOCK(so); 2163 return (error); 2164 } 2165 2166 static int 2167 biba_socket_check_relabel(struct ucred *cred, struct socket *so, 2168 struct label *solabel, struct label *newlabel) 2169 { 2170 struct mac_biba *subj, *obj, *new; 2171 int error; 2172 2173 SOCK_LOCK_ASSERT(so); 2174 2175 new = SLOT(newlabel); 2176 subj = SLOT(cred->cr_label); 2177 obj = SLOT(solabel); 2178 2179 /* 2180 * If there is a Biba label update for the socket, it may be an 2181 * update of effective. 2182 */ 2183 error = biba_atmostflags(new, MAC_BIBA_FLAG_EFFECTIVE); 2184 if (error) 2185 return (error); 2186 2187 /* 2188 * To relabel a socket, the old socket effective must be in the 2189 * subject range. 2190 */ 2191 if (!biba_effective_in_range(obj, subj)) 2192 return (EPERM); 2193 2194 /* 2195 * If the Biba label is to be changed, authorize as appropriate. 2196 */ 2197 if (new->mb_flags & MAC_BIBA_FLAG_EFFECTIVE) { 2198 /* 2199 * To relabel a socket, the new socket effective must be in 2200 * the subject range. 2201 */ 2202 if (!biba_effective_in_range(new, subj)) 2203 return (EPERM); 2204 2205 /* 2206 * To change the Biba label on the socket to contain EQUAL, 2207 * the subject must have appropriate privilege. 2208 */ 2209 if (biba_contains_equal(new)) { 2210 error = biba_subject_privileged(subj); 2211 if (error) 2212 return (error); 2213 } 2214 } 2215 2216 return (0); 2217 } 2218 2219 static int 2220 biba_socket_check_visible(struct ucred *cred, struct socket *so, 2221 struct label *solabel) 2222 { 2223 struct mac_biba *subj, *obj; 2224 2225 if (!biba_enabled) 2226 return (0); 2227 2228 subj = SLOT(cred->cr_label); 2229 obj = SLOT(solabel); 2230 2231 SOCK_LOCK(so); 2232 if (!biba_dominate_effective(obj, subj)) { 2233 SOCK_UNLOCK(so); 2234 return (ENOENT); 2235 } 2236 SOCK_UNLOCK(so); 2237 2238 return (0); 2239 } 2240 2241 static void 2242 biba_socket_create(struct ucred *cred, struct socket *so, 2243 struct label *solabel) 2244 { 2245 struct mac_biba *source, *dest; 2246 2247 source = SLOT(cred->cr_label); 2248 dest = SLOT(solabel); 2249 2250 biba_copy_effective(source, dest); 2251 } 2252 2253 static void 2254 biba_socket_create_mbuf(struct socket *so, struct label *solabel, 2255 struct mbuf *m, struct label *mlabel) 2256 { 2257 struct mac_biba *source, *dest; 2258 2259 source = SLOT(solabel); 2260 dest = SLOT(mlabel); 2261 2262 SOCK_LOCK(so); 2263 biba_copy_effective(source, dest); 2264 SOCK_UNLOCK(so); 2265 } 2266 2267 static void 2268 biba_socket_newconn(struct socket *oldso, struct label *oldsolabel, 2269 struct socket *newso, struct label *newsolabel) 2270 { 2271 struct mac_biba source, *dest; 2272 2273 SOCK_LOCK(oldso); 2274 source = *SLOT(oldsolabel); 2275 SOCK_UNLOCK(oldso); 2276 2277 dest = SLOT(newsolabel); 2278 2279 SOCK_LOCK(newso); 2280 biba_copy_effective(&source, dest); 2281 SOCK_UNLOCK(newso); 2282 } 2283 2284 static void 2285 biba_socket_relabel(struct ucred *cred, struct socket *so, 2286 struct label *solabel, struct label *newlabel) 2287 { 2288 struct mac_biba *source, *dest; 2289 2290 SOCK_LOCK_ASSERT(so); 2291 2292 source = SLOT(newlabel); 2293 dest = SLOT(solabel); 2294 2295 biba_copy(source, dest); 2296 } 2297 2298 static void 2299 biba_socketpeer_set_from_mbuf(struct mbuf *m, struct label *mlabel, 2300 struct socket *so, struct label *sopeerlabel) 2301 { 2302 struct mac_biba *source, *dest; 2303 2304 source = SLOT(mlabel); 2305 dest = SLOT(sopeerlabel); 2306 2307 SOCK_LOCK(so); 2308 biba_copy_effective(source, dest); 2309 SOCK_UNLOCK(so); 2310 } 2311 2312 static void 2313 biba_socketpeer_set_from_socket(struct socket *oldso, 2314 struct label *oldsolabel, struct socket *newso, 2315 struct label *newsopeerlabel) 2316 { 2317 struct mac_biba source, *dest; 2318 2319 SOCK_LOCK(oldso); 2320 source = *SLOT(oldsolabel); 2321 SOCK_UNLOCK(oldso); 2322 dest = SLOT(newsopeerlabel); 2323 2324 SOCK_LOCK(newso); 2325 biba_copy_effective(&source, dest); 2326 SOCK_UNLOCK(newso); 2327 } 2328 2329 static void 2330 biba_syncache_create(struct label *label, struct inpcb *inp) 2331 { 2332 struct mac_biba *source, *dest; 2333 2334 source = SLOT(inp->inp_label); 2335 dest = SLOT(label); 2336 biba_copy_effective(source, dest); 2337 } 2338 2339 static void 2340 biba_syncache_create_mbuf(struct label *sc_label, struct mbuf *m, 2341 struct label *mlabel) 2342 { 2343 struct mac_biba *source, *dest; 2344 2345 source = SLOT(sc_label); 2346 dest = SLOT(mlabel); 2347 biba_copy_effective(source, dest); 2348 } 2349 2350 static int 2351 biba_system_check_acct(struct ucred *cred, struct vnode *vp, 2352 struct label *vplabel) 2353 { 2354 struct mac_biba *subj, *obj; 2355 int error; 2356 2357 if (!biba_enabled) 2358 return (0); 2359 2360 subj = SLOT(cred->cr_label); 2361 2362 error = biba_subject_privileged(subj); 2363 if (error) 2364 return (error); 2365 2366 if (vplabel == NULL) 2367 return (0); 2368 2369 obj = SLOT(vplabel); 2370 if (!biba_high_effective(obj)) 2371 return (EACCES); 2372 2373 return (0); 2374 } 2375 2376 static int 2377 biba_system_check_auditctl(struct ucred *cred, struct vnode *vp, 2378 struct label *vplabel) 2379 { 2380 struct mac_biba *subj, *obj; 2381 int error; 2382 2383 if (!biba_enabled) 2384 return (0); 2385 2386 subj = SLOT(cred->cr_label); 2387 2388 error = biba_subject_privileged(subj); 2389 if (error) 2390 return (error); 2391 2392 if (vplabel == NULL) 2393 return (0); 2394 2395 obj = SLOT(vplabel); 2396 if (!biba_high_effective(obj)) 2397 return (EACCES); 2398 2399 return (0); 2400 } 2401 2402 static int 2403 biba_system_check_auditon(struct ucred *cred, int cmd) 2404 { 2405 struct mac_biba *subj; 2406 int error; 2407 2408 if (!biba_enabled) 2409 return (0); 2410 2411 subj = SLOT(cred->cr_label); 2412 2413 error = biba_subject_privileged(subj); 2414 if (error) 2415 return (error); 2416 2417 return (0); 2418 } 2419 2420 static int 2421 biba_system_check_swapoff(struct ucred *cred, struct vnode *vp, 2422 struct label *label) 2423 { 2424 struct mac_biba *subj; 2425 int error; 2426 2427 if (!biba_enabled) 2428 return (0); 2429 2430 subj = SLOT(cred->cr_label); 2431 2432 error = biba_subject_privileged(subj); 2433 if (error) 2434 return (error); 2435 2436 return (0); 2437 } 2438 2439 static int 2440 biba_system_check_swapon(struct ucred *cred, struct vnode *vp, 2441 struct label *vplabel) 2442 { 2443 struct mac_biba *subj, *obj; 2444 int error; 2445 2446 if (!biba_enabled) 2447 return (0); 2448 2449 subj = SLOT(cred->cr_label); 2450 obj = SLOT(vplabel); 2451 2452 error = biba_subject_privileged(subj); 2453 if (error) 2454 return (error); 2455 2456 if (!biba_high_effective(obj)) 2457 return (EACCES); 2458 2459 return (0); 2460 } 2461 2462 static int 2463 biba_system_check_sysctl(struct ucred *cred, struct sysctl_oid *oidp, 2464 void *arg1, int arg2, struct sysctl_req *req) 2465 { 2466 struct mac_biba *subj; 2467 int error; 2468 2469 if (!biba_enabled) 2470 return (0); 2471 2472 subj = SLOT(cred->cr_label); 2473 2474 /* 2475 * Treat sysctl variables without CTLFLAG_ANYBODY flag as biba/high, 2476 * but also require privilege to change them. 2477 */ 2478 if (req->newptr != NULL && (oidp->oid_kind & CTLFLAG_ANYBODY) == 0) { 2479 if (!biba_subject_dominate_high(subj)) 2480 return (EACCES); 2481 2482 error = biba_subject_privileged(subj); 2483 if (error) 2484 return (error); 2485 } 2486 2487 return (0); 2488 } 2489 2490 static void 2491 biba_sysvmsg_cleanup(struct label *msglabel) 2492 { 2493 2494 bzero(SLOT(msglabel), sizeof(struct mac_biba)); 2495 } 2496 2497 static void 2498 biba_sysvmsg_create(struct ucred *cred, struct msqid_kernel *msqkptr, 2499 struct label *msqlabel, struct msg *msgptr, struct label *msglabel) 2500 { 2501 struct mac_biba *source, *dest; 2502 2503 /* Ignore the msgq label */ 2504 source = SLOT(cred->cr_label); 2505 dest = SLOT(msglabel); 2506 2507 biba_copy_effective(source, dest); 2508 } 2509 2510 static int 2511 biba_sysvmsq_check_msgrcv(struct ucred *cred, struct msg *msgptr, 2512 struct label *msglabel) 2513 { 2514 struct mac_biba *subj, *obj; 2515 2516 if (!biba_enabled) 2517 return (0); 2518 2519 subj = SLOT(cred->cr_label); 2520 obj = SLOT(msglabel); 2521 2522 if (!biba_dominate_effective(obj, subj)) 2523 return (EACCES); 2524 2525 return (0); 2526 } 2527 2528 static int 2529 biba_sysvmsq_check_msgrmid(struct ucred *cred, struct msg *msgptr, 2530 struct label *msglabel) 2531 { 2532 struct mac_biba *subj, *obj; 2533 2534 if (!biba_enabled) 2535 return (0); 2536 2537 subj = SLOT(cred->cr_label); 2538 obj = SLOT(msglabel); 2539 2540 if (!biba_dominate_effective(subj, obj)) 2541 return (EACCES); 2542 2543 return (0); 2544 } 2545 2546 static int 2547 biba_sysvmsq_check_msqget(struct ucred *cred, struct msqid_kernel *msqkptr, 2548 struct label *msqklabel) 2549 { 2550 struct mac_biba *subj, *obj; 2551 2552 if (!biba_enabled) 2553 return (0); 2554 2555 subj = SLOT(cred->cr_label); 2556 obj = SLOT(msqklabel); 2557 2558 if (!biba_dominate_effective(obj, subj)) 2559 return (EACCES); 2560 2561 return (0); 2562 } 2563 2564 static int 2565 biba_sysvmsq_check_msqsnd(struct ucred *cred, struct msqid_kernel *msqkptr, 2566 struct label *msqklabel) 2567 { 2568 struct mac_biba *subj, *obj; 2569 2570 if (!biba_enabled) 2571 return (0); 2572 2573 subj = SLOT(cred->cr_label); 2574 obj = SLOT(msqklabel); 2575 2576 if (!biba_dominate_effective(subj, obj)) 2577 return (EACCES); 2578 2579 return (0); 2580 } 2581 2582 static int 2583 biba_sysvmsq_check_msqrcv(struct ucred *cred, struct msqid_kernel *msqkptr, 2584 struct label *msqklabel) 2585 { 2586 struct mac_biba *subj, *obj; 2587 2588 if (!biba_enabled) 2589 return (0); 2590 2591 subj = SLOT(cred->cr_label); 2592 obj = SLOT(msqklabel); 2593 2594 if (!biba_dominate_effective(obj, subj)) 2595 return (EACCES); 2596 2597 return (0); 2598 } 2599 2600 static int 2601 biba_sysvmsq_check_msqctl(struct ucred *cred, struct msqid_kernel *msqkptr, 2602 struct label *msqklabel, int cmd) 2603 { 2604 struct mac_biba *subj, *obj; 2605 2606 if (!biba_enabled) 2607 return (0); 2608 2609 subj = SLOT(cred->cr_label); 2610 obj = SLOT(msqklabel); 2611 2612 switch(cmd) { 2613 case IPC_RMID: 2614 case IPC_SET: 2615 if (!biba_dominate_effective(subj, obj)) 2616 return (EACCES); 2617 break; 2618 2619 case IPC_STAT: 2620 if (!biba_dominate_effective(obj, subj)) 2621 return (EACCES); 2622 break; 2623 2624 default: 2625 return (EACCES); 2626 } 2627 2628 return (0); 2629 } 2630 2631 static void 2632 biba_sysvmsq_cleanup(struct label *msqlabel) 2633 { 2634 2635 bzero(SLOT(msqlabel), sizeof(struct mac_biba)); 2636 } 2637 2638 static void 2639 biba_sysvmsq_create(struct ucred *cred, struct msqid_kernel *msqkptr, 2640 struct label *msqlabel) 2641 { 2642 struct mac_biba *source, *dest; 2643 2644 source = SLOT(cred->cr_label); 2645 dest = SLOT(msqlabel); 2646 2647 biba_copy_effective(source, dest); 2648 } 2649 2650 static int 2651 biba_sysvsem_check_semctl(struct ucred *cred, struct semid_kernel *semakptr, 2652 struct label *semaklabel, int cmd) 2653 { 2654 struct mac_biba *subj, *obj; 2655 2656 if (!biba_enabled) 2657 return (0); 2658 2659 subj = SLOT(cred->cr_label); 2660 obj = SLOT(semaklabel); 2661 2662 switch(cmd) { 2663 case IPC_RMID: 2664 case IPC_SET: 2665 case SETVAL: 2666 case SETALL: 2667 if (!biba_dominate_effective(subj, obj)) 2668 return (EACCES); 2669 break; 2670 2671 case IPC_STAT: 2672 case GETVAL: 2673 case GETPID: 2674 case GETNCNT: 2675 case GETZCNT: 2676 case GETALL: 2677 if (!biba_dominate_effective(obj, subj)) 2678 return (EACCES); 2679 break; 2680 2681 default: 2682 return (EACCES); 2683 } 2684 2685 return (0); 2686 } 2687 2688 static int 2689 biba_sysvsem_check_semget(struct ucred *cred, struct semid_kernel *semakptr, 2690 struct label *semaklabel) 2691 { 2692 struct mac_biba *subj, *obj; 2693 2694 if (!biba_enabled) 2695 return (0); 2696 2697 subj = SLOT(cred->cr_label); 2698 obj = SLOT(semaklabel); 2699 2700 if (!biba_dominate_effective(obj, subj)) 2701 return (EACCES); 2702 2703 return (0); 2704 } 2705 2706 static int 2707 biba_sysvsem_check_semop(struct ucred *cred, struct semid_kernel *semakptr, 2708 struct label *semaklabel, size_t accesstype) 2709 { 2710 struct mac_biba *subj, *obj; 2711 2712 if (!biba_enabled) 2713 return (0); 2714 2715 subj = SLOT(cred->cr_label); 2716 obj = SLOT(semaklabel); 2717 2718 if (accesstype & SEM_R) 2719 if (!biba_dominate_effective(obj, subj)) 2720 return (EACCES); 2721 2722 if (accesstype & SEM_A) 2723 if (!biba_dominate_effective(subj, obj)) 2724 return (EACCES); 2725 2726 return (0); 2727 } 2728 2729 static void 2730 biba_sysvsem_cleanup(struct label *semalabel) 2731 { 2732 2733 bzero(SLOT(semalabel), sizeof(struct mac_biba)); 2734 } 2735 2736 static void 2737 biba_sysvsem_create(struct ucred *cred, struct semid_kernel *semakptr, 2738 struct label *semalabel) 2739 { 2740 struct mac_biba *source, *dest; 2741 2742 source = SLOT(cred->cr_label); 2743 dest = SLOT(semalabel); 2744 2745 biba_copy_effective(source, dest); 2746 } 2747 2748 static int 2749 biba_sysvshm_check_shmat(struct ucred *cred, struct shmid_kernel *shmsegptr, 2750 struct label *shmseglabel, int shmflg) 2751 { 2752 struct mac_biba *subj, *obj; 2753 2754 if (!biba_enabled) 2755 return (0); 2756 2757 subj = SLOT(cred->cr_label); 2758 obj = SLOT(shmseglabel); 2759 2760 if (!biba_dominate_effective(obj, subj)) 2761 return (EACCES); 2762 if ((shmflg & SHM_RDONLY) == 0) { 2763 if (!biba_dominate_effective(subj, obj)) 2764 return (EACCES); 2765 } 2766 2767 return (0); 2768 } 2769 2770 static int 2771 biba_sysvshm_check_shmctl(struct ucred *cred, struct shmid_kernel *shmsegptr, 2772 struct label *shmseglabel, int cmd) 2773 { 2774 struct mac_biba *subj, *obj; 2775 2776 if (!biba_enabled) 2777 return (0); 2778 2779 subj = SLOT(cred->cr_label); 2780 obj = SLOT(shmseglabel); 2781 2782 switch(cmd) { 2783 case IPC_RMID: 2784 case IPC_SET: 2785 if (!biba_dominate_effective(subj, obj)) 2786 return (EACCES); 2787 break; 2788 2789 case IPC_STAT: 2790 case SHM_STAT: 2791 if (!biba_dominate_effective(obj, subj)) 2792 return (EACCES); 2793 break; 2794 2795 default: 2796 return (EACCES); 2797 } 2798 2799 return (0); 2800 } 2801 2802 static int 2803 biba_sysvshm_check_shmget(struct ucred *cred, struct shmid_kernel *shmsegptr, 2804 struct label *shmseglabel, int shmflg) 2805 { 2806 struct mac_biba *subj, *obj; 2807 2808 if (!biba_enabled) 2809 return (0); 2810 2811 subj = SLOT(cred->cr_label); 2812 obj = SLOT(shmseglabel); 2813 2814 if (!biba_dominate_effective(obj, subj)) 2815 return (EACCES); 2816 2817 return (0); 2818 } 2819 2820 static void 2821 biba_sysvshm_cleanup(struct label *shmlabel) 2822 { 2823 2824 bzero(SLOT(shmlabel), sizeof(struct mac_biba)); 2825 } 2826 2827 static void 2828 biba_sysvshm_create(struct ucred *cred, struct shmid_kernel *shmsegptr, 2829 struct label *shmlabel) 2830 { 2831 struct mac_biba *source, *dest; 2832 2833 source = SLOT(cred->cr_label); 2834 dest = SLOT(shmlabel); 2835 2836 biba_copy_effective(source, dest); 2837 } 2838 2839 static int 2840 biba_vnode_associate_extattr(struct mount *mp, struct label *mplabel, 2841 struct vnode *vp, struct label *vplabel) 2842 { 2843 struct mac_biba mb_temp, *source, *dest; 2844 int buflen, error; 2845 2846 source = SLOT(mplabel); 2847 dest = SLOT(vplabel); 2848 2849 buflen = sizeof(mb_temp); 2850 bzero(&mb_temp, buflen); 2851 2852 error = vn_extattr_get(vp, IO_NODELOCKED, MAC_BIBA_EXTATTR_NAMESPACE, 2853 MAC_BIBA_EXTATTR_NAME, &buflen, (char *) &mb_temp, curthread); 2854 if (error == ENOATTR || error == EOPNOTSUPP) { 2855 /* Fall back to the mntlabel. */ 2856 biba_copy_effective(source, dest); 2857 return (0); 2858 } else if (error) 2859 return (error); 2860 2861 if (buflen != sizeof(mb_temp)) { 2862 printf("biba_vnode_associate_extattr: bad size %d\n", 2863 buflen); 2864 return (EPERM); 2865 } 2866 if (biba_valid(&mb_temp) != 0) { 2867 printf("biba_vnode_associate_extattr: invalid\n"); 2868 return (EPERM); 2869 } 2870 if ((mb_temp.mb_flags & MAC_BIBA_FLAGS_BOTH) != 2871 MAC_BIBA_FLAG_EFFECTIVE) { 2872 printf("biba_vnode_associate_extattr: not effective\n"); 2873 return (EPERM); 2874 } 2875 2876 biba_copy_effective(&mb_temp, dest); 2877 return (0); 2878 } 2879 2880 static void 2881 biba_vnode_associate_singlelabel(struct mount *mp, struct label *mplabel, 2882 struct vnode *vp, struct label *vplabel) 2883 { 2884 struct mac_biba *source, *dest; 2885 2886 source = SLOT(mplabel); 2887 dest = SLOT(vplabel); 2888 2889 biba_copy_effective(source, dest); 2890 } 2891 2892 static int 2893 biba_vnode_check_chdir(struct ucred *cred, struct vnode *dvp, 2894 struct label *dvplabel) 2895 { 2896 struct mac_biba *subj, *obj; 2897 2898 if (!biba_enabled) 2899 return (0); 2900 2901 subj = SLOT(cred->cr_label); 2902 obj = SLOT(dvplabel); 2903 2904 if (!biba_dominate_effective(obj, subj)) 2905 return (EACCES); 2906 2907 return (0); 2908 } 2909 2910 static int 2911 biba_vnode_check_chroot(struct ucred *cred, struct vnode *dvp, 2912 struct label *dvplabel) 2913 { 2914 struct mac_biba *subj, *obj; 2915 2916 if (!biba_enabled) 2917 return (0); 2918 2919 subj = SLOT(cred->cr_label); 2920 obj = SLOT(dvplabel); 2921 2922 if (!biba_dominate_effective(obj, subj)) 2923 return (EACCES); 2924 2925 return (0); 2926 } 2927 2928 static int 2929 biba_vnode_check_create(struct ucred *cred, struct vnode *dvp, 2930 struct label *dvplabel, struct componentname *cnp, struct vattr *vap) 2931 { 2932 struct mac_biba *subj, *obj; 2933 2934 if (!biba_enabled) 2935 return (0); 2936 2937 subj = SLOT(cred->cr_label); 2938 obj = SLOT(dvplabel); 2939 2940 if (!biba_dominate_effective(subj, obj)) 2941 return (EACCES); 2942 2943 return (0); 2944 } 2945 2946 static int 2947 biba_vnode_check_deleteacl(struct ucred *cred, struct vnode *vp, 2948 struct label *vplabel, acl_type_t type) 2949 { 2950 struct mac_biba *subj, *obj; 2951 2952 if (!biba_enabled) 2953 return (0); 2954 2955 subj = SLOT(cred->cr_label); 2956 obj = SLOT(vplabel); 2957 2958 if (!biba_dominate_effective(subj, obj)) 2959 return (EACCES); 2960 2961 return (0); 2962 } 2963 2964 static int 2965 biba_vnode_check_deleteextattr(struct ucred *cred, struct vnode *vp, 2966 struct label *vplabel, int attrnamespace, const char *name) 2967 { 2968 struct mac_biba *subj, *obj; 2969 2970 if (!biba_enabled) 2971 return (0); 2972 2973 subj = SLOT(cred->cr_label); 2974 obj = SLOT(vplabel); 2975 2976 if (!biba_dominate_effective(subj, obj)) 2977 return (EACCES); 2978 2979 return (0); 2980 } 2981 2982 static int 2983 biba_vnode_check_exec(struct ucred *cred, struct vnode *vp, 2984 struct label *vplabel, struct image_params *imgp, 2985 struct label *execlabel) 2986 { 2987 struct mac_biba *subj, *obj, *exec; 2988 int error; 2989 2990 if (execlabel != NULL) { 2991 /* 2992 * We currently don't permit labels to be changed at 2993 * exec-time as part of Biba, so disallow non-NULL Biba label 2994 * elements in the execlabel. 2995 */ 2996 exec = SLOT(execlabel); 2997 error = biba_atmostflags(exec, 0); 2998 if (error) 2999 return (error); 3000 } 3001 3002 if (!biba_enabled) 3003 return (0); 3004 3005 subj = SLOT(cred->cr_label); 3006 obj = SLOT(vplabel); 3007 3008 if (!biba_dominate_effective(obj, subj)) 3009 return (EACCES); 3010 3011 return (0); 3012 } 3013 3014 static int 3015 biba_vnode_check_getacl(struct ucred *cred, struct vnode *vp, 3016 struct label *vplabel, acl_type_t type) 3017 { 3018 struct mac_biba *subj, *obj; 3019 3020 if (!biba_enabled) 3021 return (0); 3022 3023 subj = SLOT(cred->cr_label); 3024 obj = SLOT(vplabel); 3025 3026 if (!biba_dominate_effective(obj, subj)) 3027 return (EACCES); 3028 3029 return (0); 3030 } 3031 3032 static int 3033 biba_vnode_check_getextattr(struct ucred *cred, struct vnode *vp, 3034 struct label *vplabel, int attrnamespace, const char *name) 3035 { 3036 struct mac_biba *subj, *obj; 3037 3038 if (!biba_enabled) 3039 return (0); 3040 3041 subj = SLOT(cred->cr_label); 3042 obj = SLOT(vplabel); 3043 3044 if (!biba_dominate_effective(obj, subj)) 3045 return (EACCES); 3046 3047 return (0); 3048 } 3049 3050 static int 3051 biba_vnode_check_link(struct ucred *cred, struct vnode *dvp, 3052 struct label *dvplabel, struct vnode *vp, struct label *vplabel, 3053 struct componentname *cnp) 3054 { 3055 struct mac_biba *subj, *obj; 3056 3057 if (!biba_enabled) 3058 return (0); 3059 3060 subj = SLOT(cred->cr_label); 3061 obj = SLOT(dvplabel); 3062 3063 if (!biba_dominate_effective(subj, obj)) 3064 return (EACCES); 3065 3066 obj = SLOT(vplabel); 3067 3068 if (!biba_dominate_effective(subj, obj)) 3069 return (EACCES); 3070 3071 return (0); 3072 } 3073 3074 static int 3075 biba_vnode_check_listextattr(struct ucred *cred, struct vnode *vp, 3076 struct label *vplabel, int attrnamespace) 3077 { 3078 struct mac_biba *subj, *obj; 3079 3080 if (!biba_enabled) 3081 return (0); 3082 3083 subj = SLOT(cred->cr_label); 3084 obj = SLOT(vplabel); 3085 3086 if (!biba_dominate_effective(obj, subj)) 3087 return (EACCES); 3088 3089 return (0); 3090 } 3091 3092 static int 3093 biba_vnode_check_lookup(struct ucred *cred, struct vnode *dvp, 3094 struct label *dvplabel, struct componentname *cnp) 3095 { 3096 struct mac_biba *subj, *obj; 3097 3098 if (!biba_enabled) 3099 return (0); 3100 3101 subj = SLOT(cred->cr_label); 3102 obj = SLOT(dvplabel); 3103 3104 if (!biba_dominate_effective(obj, subj)) 3105 return (EACCES); 3106 3107 return (0); 3108 } 3109 3110 static int 3111 biba_vnode_check_mmap(struct ucred *cred, struct vnode *vp, 3112 struct label *vplabel, int prot, int flags) 3113 { 3114 struct mac_biba *subj, *obj; 3115 3116 /* 3117 * Rely on the use of open()-time protections to handle 3118 * non-revocation cases. 3119 */ 3120 if (!biba_enabled || !revocation_enabled) 3121 return (0); 3122 3123 subj = SLOT(cred->cr_label); 3124 obj = SLOT(vplabel); 3125 3126 if (prot & (VM_PROT_READ | VM_PROT_EXECUTE)) { 3127 if (!biba_dominate_effective(obj, subj)) 3128 return (EACCES); 3129 } 3130 if (((prot & VM_PROT_WRITE) != 0) && ((flags & MAP_SHARED) != 0)) { 3131 if (!biba_dominate_effective(subj, obj)) 3132 return (EACCES); 3133 } 3134 3135 return (0); 3136 } 3137 3138 static int 3139 biba_vnode_check_open(struct ucred *cred, struct vnode *vp, 3140 struct label *vplabel, accmode_t accmode) 3141 { 3142 struct mac_biba *subj, *obj; 3143 3144 if (!biba_enabled) 3145 return (0); 3146 3147 subj = SLOT(cred->cr_label); 3148 obj = SLOT(vplabel); 3149 3150 /* XXX privilege override for admin? */ 3151 if (accmode & (VREAD | VEXEC | VSTAT_PERMS)) { 3152 if (!biba_dominate_effective(obj, subj)) 3153 return (EACCES); 3154 } 3155 if (accmode & VMODIFY_PERMS) { 3156 if (!biba_dominate_effective(subj, obj)) 3157 return (EACCES); 3158 } 3159 3160 return (0); 3161 } 3162 3163 static int 3164 biba_vnode_check_poll(struct ucred *active_cred, struct ucred *file_cred, 3165 struct vnode *vp, struct label *vplabel) 3166 { 3167 struct mac_biba *subj, *obj; 3168 3169 if (!biba_enabled || !revocation_enabled) 3170 return (0); 3171 3172 subj = SLOT(active_cred->cr_label); 3173 obj = SLOT(vplabel); 3174 3175 if (!biba_dominate_effective(obj, subj)) 3176 return (EACCES); 3177 3178 return (0); 3179 } 3180 3181 static int 3182 biba_vnode_check_read(struct ucred *active_cred, struct ucred *file_cred, 3183 struct vnode *vp, struct label *vplabel) 3184 { 3185 struct mac_biba *subj, *obj; 3186 3187 if (!biba_enabled || !revocation_enabled) 3188 return (0); 3189 3190 subj = SLOT(active_cred->cr_label); 3191 obj = SLOT(vplabel); 3192 3193 if (!biba_dominate_effective(obj, subj)) 3194 return (EACCES); 3195 3196 return (0); 3197 } 3198 3199 static int 3200 biba_vnode_check_readdir(struct ucred *cred, struct vnode *dvp, 3201 struct label *dvplabel) 3202 { 3203 struct mac_biba *subj, *obj; 3204 3205 if (!biba_enabled) 3206 return (0); 3207 3208 subj = SLOT(cred->cr_label); 3209 obj = SLOT(dvplabel); 3210 3211 if (!biba_dominate_effective(obj, subj)) 3212 return (EACCES); 3213 3214 return (0); 3215 } 3216 3217 static int 3218 biba_vnode_check_readlink(struct ucred *cred, struct vnode *vp, 3219 struct label *vplabel) 3220 { 3221 struct mac_biba *subj, *obj; 3222 3223 if (!biba_enabled) 3224 return (0); 3225 3226 subj = SLOT(cred->cr_label); 3227 obj = SLOT(vplabel); 3228 3229 if (!biba_dominate_effective(obj, subj)) 3230 return (EACCES); 3231 3232 return (0); 3233 } 3234 3235 static int 3236 biba_vnode_check_relabel(struct ucred *cred, struct vnode *vp, 3237 struct label *vplabel, struct label *newlabel) 3238 { 3239 struct mac_biba *old, *new, *subj; 3240 int error; 3241 3242 old = SLOT(vplabel); 3243 new = SLOT(newlabel); 3244 subj = SLOT(cred->cr_label); 3245 3246 /* 3247 * If there is a Biba label update for the vnode, it must be a 3248 * effective label. 3249 */ 3250 error = biba_atmostflags(new, MAC_BIBA_FLAG_EFFECTIVE); 3251 if (error) 3252 return (error); 3253 3254 /* 3255 * To perform a relabel of the vnode (Biba label or not), Biba must 3256 * authorize the relabel. 3257 */ 3258 if (!biba_effective_in_range(old, subj)) 3259 return (EPERM); 3260 3261 /* 3262 * If the Biba label is to be changed, authorize as appropriate. 3263 */ 3264 if (new->mb_flags & MAC_BIBA_FLAG_EFFECTIVE) { 3265 /* 3266 * To change the Biba label on a vnode, the new vnode label 3267 * must be in the subject range. 3268 */ 3269 if (!biba_effective_in_range(new, subj)) 3270 return (EPERM); 3271 3272 /* 3273 * To change the Biba label on the vnode to be EQUAL, the 3274 * subject must have appropriate privilege. 3275 */ 3276 if (biba_contains_equal(new)) { 3277 error = biba_subject_privileged(subj); 3278 if (error) 3279 return (error); 3280 } 3281 } 3282 3283 return (0); 3284 } 3285 3286 static int 3287 biba_vnode_check_rename_from(struct ucred *cred, struct vnode *dvp, 3288 struct label *dvplabel, struct vnode *vp, struct label *vplabel, 3289 struct componentname *cnp) 3290 { 3291 struct mac_biba *subj, *obj; 3292 3293 if (!biba_enabled) 3294 return (0); 3295 3296 subj = SLOT(cred->cr_label); 3297 obj = SLOT(dvplabel); 3298 3299 if (!biba_dominate_effective(subj, obj)) 3300 return (EACCES); 3301 3302 obj = SLOT(vplabel); 3303 3304 if (!biba_dominate_effective(subj, obj)) 3305 return (EACCES); 3306 3307 return (0); 3308 } 3309 3310 static int 3311 biba_vnode_check_rename_to(struct ucred *cred, struct vnode *dvp, 3312 struct label *dvplabel, struct vnode *vp, struct label *vplabel, 3313 int samedir, struct componentname *cnp) 3314 { 3315 struct mac_biba *subj, *obj; 3316 3317 if (!biba_enabled) 3318 return (0); 3319 3320 subj = SLOT(cred->cr_label); 3321 obj = SLOT(dvplabel); 3322 3323 if (!biba_dominate_effective(subj, obj)) 3324 return (EACCES); 3325 3326 if (vp != NULL) { 3327 obj = SLOT(vplabel); 3328 3329 if (!biba_dominate_effective(subj, obj)) 3330 return (EACCES); 3331 } 3332 3333 return (0); 3334 } 3335 3336 static int 3337 biba_vnode_check_revoke(struct ucred *cred, struct vnode *vp, 3338 struct label *vplabel) 3339 { 3340 struct mac_biba *subj, *obj; 3341 3342 if (!biba_enabled) 3343 return (0); 3344 3345 subj = SLOT(cred->cr_label); 3346 obj = SLOT(vplabel); 3347 3348 if (!biba_dominate_effective(subj, obj)) 3349 return (EACCES); 3350 3351 return (0); 3352 } 3353 3354 static int 3355 biba_vnode_check_setacl(struct ucred *cred, struct vnode *vp, 3356 struct label *vplabel, acl_type_t type, struct acl *acl) 3357 { 3358 struct mac_biba *subj, *obj; 3359 3360 if (!biba_enabled) 3361 return (0); 3362 3363 subj = SLOT(cred->cr_label); 3364 obj = SLOT(vplabel); 3365 3366 if (!biba_dominate_effective(subj, obj)) 3367 return (EACCES); 3368 3369 return (0); 3370 } 3371 3372 static int 3373 biba_vnode_check_setextattr(struct ucred *cred, struct vnode *vp, 3374 struct label *vplabel, int attrnamespace, const char *name) 3375 { 3376 struct mac_biba *subj, *obj; 3377 3378 if (!biba_enabled) 3379 return (0); 3380 3381 subj = SLOT(cred->cr_label); 3382 obj = SLOT(vplabel); 3383 3384 if (!biba_dominate_effective(subj, obj)) 3385 return (EACCES); 3386 3387 /* XXX: protect the MAC EA in a special way? */ 3388 3389 return (0); 3390 } 3391 3392 static int 3393 biba_vnode_check_setflags(struct ucred *cred, struct vnode *vp, 3394 struct label *vplabel, u_long flags) 3395 { 3396 struct mac_biba *subj, *obj; 3397 3398 if (!biba_enabled) 3399 return (0); 3400 3401 subj = SLOT(cred->cr_label); 3402 obj = SLOT(vplabel); 3403 3404 if (!biba_dominate_effective(subj, obj)) 3405 return (EACCES); 3406 3407 return (0); 3408 } 3409 3410 static int 3411 biba_vnode_check_setmode(struct ucred *cred, struct vnode *vp, 3412 struct label *vplabel, mode_t mode) 3413 { 3414 struct mac_biba *subj, *obj; 3415 3416 if (!biba_enabled) 3417 return (0); 3418 3419 subj = SLOT(cred->cr_label); 3420 obj = SLOT(vplabel); 3421 3422 if (!biba_dominate_effective(subj, obj)) 3423 return (EACCES); 3424 3425 return (0); 3426 } 3427 3428 static int 3429 biba_vnode_check_setowner(struct ucred *cred, struct vnode *vp, 3430 struct label *vplabel, uid_t uid, gid_t gid) 3431 { 3432 struct mac_biba *subj, *obj; 3433 3434 if (!biba_enabled) 3435 return (0); 3436 3437 subj = SLOT(cred->cr_label); 3438 obj = SLOT(vplabel); 3439 3440 if (!biba_dominate_effective(subj, obj)) 3441 return (EACCES); 3442 3443 return (0); 3444 } 3445 3446 static int 3447 biba_vnode_check_setutimes(struct ucred *cred, struct vnode *vp, 3448 struct label *vplabel, struct timespec atime, struct timespec mtime) 3449 { 3450 struct mac_biba *subj, *obj; 3451 3452 if (!biba_enabled) 3453 return (0); 3454 3455 subj = SLOT(cred->cr_label); 3456 obj = SLOT(vplabel); 3457 3458 if (!biba_dominate_effective(subj, obj)) 3459 return (EACCES); 3460 3461 return (0); 3462 } 3463 3464 static int 3465 biba_vnode_check_stat(struct ucred *active_cred, struct ucred *file_cred, 3466 struct vnode *vp, struct label *vplabel) 3467 { 3468 struct mac_biba *subj, *obj; 3469 3470 if (!biba_enabled) 3471 return (0); 3472 3473 subj = SLOT(active_cred->cr_label); 3474 obj = SLOT(vplabel); 3475 3476 if (!biba_dominate_effective(obj, subj)) 3477 return (EACCES); 3478 3479 return (0); 3480 } 3481 3482 static int 3483 biba_vnode_check_unlink(struct ucred *cred, struct vnode *dvp, 3484 struct label *dvplabel, struct vnode *vp, struct label *vplabel, 3485 struct componentname *cnp) 3486 { 3487 struct mac_biba *subj, *obj; 3488 3489 if (!biba_enabled) 3490 return (0); 3491 3492 subj = SLOT(cred->cr_label); 3493 obj = SLOT(dvplabel); 3494 3495 if (!biba_dominate_effective(subj, obj)) 3496 return (EACCES); 3497 3498 obj = SLOT(vplabel); 3499 3500 if (!biba_dominate_effective(subj, obj)) 3501 return (EACCES); 3502 3503 return (0); 3504 } 3505 3506 static int 3507 biba_vnode_check_write(struct ucred *active_cred, 3508 struct ucred *file_cred, struct vnode *vp, struct label *vplabel) 3509 { 3510 struct mac_biba *subj, *obj; 3511 3512 if (!biba_enabled || !revocation_enabled) 3513 return (0); 3514 3515 subj = SLOT(active_cred->cr_label); 3516 obj = SLOT(vplabel); 3517 3518 if (!biba_dominate_effective(subj, obj)) 3519 return (EACCES); 3520 3521 return (0); 3522 } 3523 3524 static int 3525 biba_vnode_create_extattr(struct ucred *cred, struct mount *mp, 3526 struct label *mplabel, struct vnode *dvp, struct label *dvplabel, 3527 struct vnode *vp, struct label *vplabel, struct componentname *cnp) 3528 { 3529 struct mac_biba *source, *dest, mb_temp; 3530 size_t buflen; 3531 int error; 3532 3533 buflen = sizeof(mb_temp); 3534 bzero(&mb_temp, buflen); 3535 3536 source = SLOT(cred->cr_label); 3537 dest = SLOT(vplabel); 3538 biba_copy_effective(source, &mb_temp); 3539 3540 error = vn_extattr_set(vp, IO_NODELOCKED, MAC_BIBA_EXTATTR_NAMESPACE, 3541 MAC_BIBA_EXTATTR_NAME, buflen, (char *) &mb_temp, curthread); 3542 if (error == 0) 3543 biba_copy_effective(source, dest); 3544 return (error); 3545 } 3546 3547 static void 3548 biba_vnode_relabel(struct ucred *cred, struct vnode *vp, 3549 struct label *vplabel, struct label *newlabel) 3550 { 3551 struct mac_biba *source, *dest; 3552 3553 source = SLOT(newlabel); 3554 dest = SLOT(vplabel); 3555 3556 biba_copy(source, dest); 3557 } 3558 3559 static int 3560 biba_vnode_setlabel_extattr(struct ucred *cred, struct vnode *vp, 3561 struct label *vplabel, struct label *intlabel) 3562 { 3563 struct mac_biba *source, mb_temp; 3564 size_t buflen; 3565 int error; 3566 3567 buflen = sizeof(mb_temp); 3568 bzero(&mb_temp, buflen); 3569 3570 source = SLOT(intlabel); 3571 if ((source->mb_flags & MAC_BIBA_FLAG_EFFECTIVE) == 0) 3572 return (0); 3573 3574 biba_copy_effective(source, &mb_temp); 3575 3576 error = vn_extattr_set(vp, IO_NODELOCKED, MAC_BIBA_EXTATTR_NAMESPACE, 3577 MAC_BIBA_EXTATTR_NAME, buflen, (char *) &mb_temp, curthread); 3578 return (error); 3579 } 3580 3581 static struct mac_policy_ops mac_biba_ops = 3582 { 3583 .mpo_init = biba_init, 3584 3585 .mpo_bpfdesc_check_receive = biba_bpfdesc_check_receive, 3586 .mpo_bpfdesc_create = biba_bpfdesc_create, 3587 .mpo_bpfdesc_create_mbuf = biba_bpfdesc_create_mbuf, 3588 .mpo_bpfdesc_destroy_label = biba_destroy_label, 3589 .mpo_bpfdesc_init_label = biba_init_label, 3590 3591 .mpo_cred_associate_nfsd = biba_cred_associate_nfsd, 3592 .mpo_cred_check_relabel = biba_cred_check_relabel, 3593 .mpo_cred_check_visible = biba_cred_check_visible, 3594 .mpo_cred_copy_label = biba_copy_label, 3595 .mpo_cred_create_init = biba_cred_create_init, 3596 .mpo_cred_create_swapper = biba_cred_create_swapper, 3597 .mpo_cred_destroy_label = biba_destroy_label, 3598 .mpo_cred_externalize_label = biba_externalize_label, 3599 .mpo_cred_init_label = biba_init_label, 3600 .mpo_cred_internalize_label = biba_internalize_label, 3601 .mpo_cred_relabel = biba_cred_relabel, 3602 3603 .mpo_devfs_create_device = biba_devfs_create_device, 3604 .mpo_devfs_create_directory = biba_devfs_create_directory, 3605 .mpo_devfs_create_symlink = biba_devfs_create_symlink, 3606 .mpo_devfs_destroy_label = biba_destroy_label, 3607 .mpo_devfs_init_label = biba_init_label, 3608 .mpo_devfs_update = biba_devfs_update, 3609 .mpo_devfs_vnode_associate = biba_devfs_vnode_associate, 3610 3611 .mpo_ifnet_check_relabel = biba_ifnet_check_relabel, 3612 .mpo_ifnet_check_transmit = biba_ifnet_check_transmit, 3613 .mpo_ifnet_copy_label = biba_copy_label, 3614 .mpo_ifnet_create = biba_ifnet_create, 3615 .mpo_ifnet_create_mbuf = biba_ifnet_create_mbuf, 3616 .mpo_ifnet_destroy_label = biba_destroy_label, 3617 .mpo_ifnet_externalize_label = biba_externalize_label, 3618 .mpo_ifnet_init_label = biba_init_label, 3619 .mpo_ifnet_internalize_label = biba_internalize_label, 3620 .mpo_ifnet_relabel = biba_ifnet_relabel, 3621 3622 .mpo_inpcb_check_deliver = biba_inpcb_check_deliver, 3623 .mpo_inpcb_check_visible = biba_inpcb_check_visible, 3624 .mpo_inpcb_create = biba_inpcb_create, 3625 .mpo_inpcb_create_mbuf = biba_inpcb_create_mbuf, 3626 .mpo_inpcb_destroy_label = biba_destroy_label, 3627 .mpo_inpcb_init_label = biba_init_label_waitcheck, 3628 .mpo_inpcb_sosetlabel = biba_inpcb_sosetlabel, 3629 3630 .mpo_ip6q_create = biba_ip6q_create, 3631 .mpo_ip6q_destroy_label = biba_destroy_label, 3632 .mpo_ip6q_init_label = biba_init_label_waitcheck, 3633 .mpo_ip6q_match = biba_ip6q_match, 3634 .mpo_ip6q_reassemble = biba_ip6q_reassemble, 3635 .mpo_ip6q_update = biba_ip6q_update, 3636 3637 .mpo_ipq_create = biba_ipq_create, 3638 .mpo_ipq_destroy_label = biba_destroy_label, 3639 .mpo_ipq_init_label = biba_init_label_waitcheck, 3640 .mpo_ipq_match = biba_ipq_match, 3641 .mpo_ipq_reassemble = biba_ipq_reassemble, 3642 .mpo_ipq_update = biba_ipq_update, 3643 3644 .mpo_kld_check_load = biba_kld_check_load, 3645 3646 .mpo_mbuf_copy_label = biba_copy_label, 3647 .mpo_mbuf_destroy_label = biba_destroy_label, 3648 .mpo_mbuf_init_label = biba_init_label_waitcheck, 3649 3650 .mpo_mount_check_stat = biba_mount_check_stat, 3651 .mpo_mount_create = biba_mount_create, 3652 .mpo_mount_destroy_label = biba_destroy_label, 3653 .mpo_mount_init_label = biba_init_label, 3654 3655 .mpo_netatalk_aarp_send = biba_netatalk_aarp_send, 3656 3657 .mpo_netinet_arp_send = biba_netinet_arp_send, 3658 .mpo_netinet_firewall_reply = biba_netinet_firewall_reply, 3659 .mpo_netinet_firewall_send = biba_netinet_firewall_send, 3660 .mpo_netinet_fragment = biba_netinet_fragment, 3661 .mpo_netinet_icmp_reply = biba_netinet_icmp_reply, 3662 .mpo_netinet_igmp_send = biba_netinet_igmp_send, 3663 3664 .mpo_netinet6_nd6_send = biba_netinet6_nd6_send, 3665 3666 .mpo_pipe_check_ioctl = biba_pipe_check_ioctl, 3667 .mpo_pipe_check_poll = biba_pipe_check_poll, 3668 .mpo_pipe_check_read = biba_pipe_check_read, 3669 .mpo_pipe_check_relabel = biba_pipe_check_relabel, 3670 .mpo_pipe_check_stat = biba_pipe_check_stat, 3671 .mpo_pipe_check_write = biba_pipe_check_write, 3672 .mpo_pipe_copy_label = biba_copy_label, 3673 .mpo_pipe_create = biba_pipe_create, 3674 .mpo_pipe_destroy_label = biba_destroy_label, 3675 .mpo_pipe_externalize_label = biba_externalize_label, 3676 .mpo_pipe_init_label = biba_init_label, 3677 .mpo_pipe_internalize_label = biba_internalize_label, 3678 .mpo_pipe_relabel = biba_pipe_relabel, 3679 3680 .mpo_posixsem_check_getvalue = biba_posixsem_check_rdonly, 3681 .mpo_posixsem_check_open = biba_posixsem_check_openunlink, 3682 .mpo_posixsem_check_post = biba_posixsem_check_write, 3683 .mpo_posixsem_check_setmode = biba_posixsem_check_setmode, 3684 .mpo_posixsem_check_setowner = biba_posixsem_check_setowner, 3685 .mpo_posixsem_check_stat = biba_posixsem_check_rdonly, 3686 .mpo_posixsem_check_unlink = biba_posixsem_check_openunlink, 3687 .mpo_posixsem_check_wait = biba_posixsem_check_write, 3688 .mpo_posixsem_create = biba_posixsem_create, 3689 .mpo_posixsem_destroy_label = biba_destroy_label, 3690 .mpo_posixsem_init_label = biba_init_label, 3691 3692 .mpo_posixshm_check_mmap = biba_posixshm_check_mmap, 3693 .mpo_posixshm_check_open = biba_posixshm_check_open, 3694 .mpo_posixshm_check_read = biba_posixshm_check_read, 3695 .mpo_posixshm_check_setmode = biba_posixshm_check_setmode, 3696 .mpo_posixshm_check_setowner = biba_posixshm_check_setowner, 3697 .mpo_posixshm_check_stat = biba_posixshm_check_stat, 3698 .mpo_posixshm_check_truncate = biba_posixshm_check_truncate, 3699 .mpo_posixshm_check_unlink = biba_posixshm_check_unlink, 3700 .mpo_posixshm_check_write = biba_posixshm_check_write, 3701 .mpo_posixshm_create = biba_posixshm_create, 3702 .mpo_posixshm_destroy_label = biba_destroy_label, 3703 .mpo_posixshm_init_label = biba_init_label, 3704 3705 .mpo_priv_check = biba_priv_check, 3706 3707 .mpo_proc_check_debug = biba_proc_check_debug, 3708 .mpo_proc_check_sched = biba_proc_check_sched, 3709 .mpo_proc_check_signal = biba_proc_check_signal, 3710 3711 .mpo_socket_check_deliver = biba_socket_check_deliver, 3712 .mpo_socket_check_relabel = biba_socket_check_relabel, 3713 .mpo_socket_check_visible = biba_socket_check_visible, 3714 .mpo_socket_copy_label = biba_copy_label, 3715 .mpo_socket_create = biba_socket_create, 3716 .mpo_socket_create_mbuf = biba_socket_create_mbuf, 3717 .mpo_socket_destroy_label = biba_destroy_label, 3718 .mpo_socket_externalize_label = biba_externalize_label, 3719 .mpo_socket_init_label = biba_init_label_waitcheck, 3720 .mpo_socket_internalize_label = biba_internalize_label, 3721 .mpo_socket_newconn = biba_socket_newconn, 3722 .mpo_socket_relabel = biba_socket_relabel, 3723 3724 .mpo_socketpeer_destroy_label = biba_destroy_label, 3725 .mpo_socketpeer_externalize_label = biba_externalize_label, 3726 .mpo_socketpeer_init_label = biba_init_label_waitcheck, 3727 .mpo_socketpeer_set_from_mbuf = biba_socketpeer_set_from_mbuf, 3728 .mpo_socketpeer_set_from_socket = biba_socketpeer_set_from_socket, 3729 3730 .mpo_syncache_create = biba_syncache_create, 3731 .mpo_syncache_create_mbuf = biba_syncache_create_mbuf, 3732 .mpo_syncache_destroy_label = biba_destroy_label, 3733 .mpo_syncache_init_label = biba_init_label_waitcheck, 3734 3735 .mpo_system_check_acct = biba_system_check_acct, 3736 .mpo_system_check_auditctl = biba_system_check_auditctl, 3737 .mpo_system_check_auditon = biba_system_check_auditon, 3738 .mpo_system_check_swapoff = biba_system_check_swapoff, 3739 .mpo_system_check_swapon = biba_system_check_swapon, 3740 .mpo_system_check_sysctl = biba_system_check_sysctl, 3741 3742 .mpo_sysvmsg_cleanup = biba_sysvmsg_cleanup, 3743 .mpo_sysvmsg_create = biba_sysvmsg_create, 3744 .mpo_sysvmsg_destroy_label = biba_destroy_label, 3745 .mpo_sysvmsg_init_label = biba_init_label, 3746 3747 .mpo_sysvmsq_check_msgrcv = biba_sysvmsq_check_msgrcv, 3748 .mpo_sysvmsq_check_msgrmid = biba_sysvmsq_check_msgrmid, 3749 .mpo_sysvmsq_check_msqget = biba_sysvmsq_check_msqget, 3750 .mpo_sysvmsq_check_msqsnd = biba_sysvmsq_check_msqsnd, 3751 .mpo_sysvmsq_check_msqrcv = biba_sysvmsq_check_msqrcv, 3752 .mpo_sysvmsq_check_msqctl = biba_sysvmsq_check_msqctl, 3753 .mpo_sysvmsq_cleanup = biba_sysvmsq_cleanup, 3754 .mpo_sysvmsq_create = biba_sysvmsq_create, 3755 .mpo_sysvmsq_destroy_label = biba_destroy_label, 3756 .mpo_sysvmsq_init_label = biba_init_label, 3757 3758 .mpo_sysvsem_check_semctl = biba_sysvsem_check_semctl, 3759 .mpo_sysvsem_check_semget = biba_sysvsem_check_semget, 3760 .mpo_sysvsem_check_semop = biba_sysvsem_check_semop, 3761 .mpo_sysvsem_cleanup = biba_sysvsem_cleanup, 3762 .mpo_sysvsem_create = biba_sysvsem_create, 3763 .mpo_sysvsem_destroy_label = biba_destroy_label, 3764 .mpo_sysvsem_init_label = biba_init_label, 3765 3766 .mpo_sysvshm_check_shmat = biba_sysvshm_check_shmat, 3767 .mpo_sysvshm_check_shmctl = biba_sysvshm_check_shmctl, 3768 .mpo_sysvshm_check_shmget = biba_sysvshm_check_shmget, 3769 .mpo_sysvshm_cleanup = biba_sysvshm_cleanup, 3770 .mpo_sysvshm_create = biba_sysvshm_create, 3771 .mpo_sysvshm_destroy_label = biba_destroy_label, 3772 .mpo_sysvshm_init_label = biba_init_label, 3773 3774 .mpo_vnode_associate_extattr = biba_vnode_associate_extattr, 3775 .mpo_vnode_associate_singlelabel = biba_vnode_associate_singlelabel, 3776 .mpo_vnode_check_access = biba_vnode_check_open, 3777 .mpo_vnode_check_chdir = biba_vnode_check_chdir, 3778 .mpo_vnode_check_chroot = biba_vnode_check_chroot, 3779 .mpo_vnode_check_create = biba_vnode_check_create, 3780 .mpo_vnode_check_deleteacl = biba_vnode_check_deleteacl, 3781 .mpo_vnode_check_deleteextattr = biba_vnode_check_deleteextattr, 3782 .mpo_vnode_check_exec = biba_vnode_check_exec, 3783 .mpo_vnode_check_getacl = biba_vnode_check_getacl, 3784 .mpo_vnode_check_getextattr = biba_vnode_check_getextattr, 3785 .mpo_vnode_check_link = biba_vnode_check_link, 3786 .mpo_vnode_check_listextattr = biba_vnode_check_listextattr, 3787 .mpo_vnode_check_lookup = biba_vnode_check_lookup, 3788 .mpo_vnode_check_mmap = biba_vnode_check_mmap, 3789 .mpo_vnode_check_open = biba_vnode_check_open, 3790 .mpo_vnode_check_poll = biba_vnode_check_poll, 3791 .mpo_vnode_check_read = biba_vnode_check_read, 3792 .mpo_vnode_check_readdir = biba_vnode_check_readdir, 3793 .mpo_vnode_check_readlink = biba_vnode_check_readlink, 3794 .mpo_vnode_check_relabel = biba_vnode_check_relabel, 3795 .mpo_vnode_check_rename_from = biba_vnode_check_rename_from, 3796 .mpo_vnode_check_rename_to = biba_vnode_check_rename_to, 3797 .mpo_vnode_check_revoke = biba_vnode_check_revoke, 3798 .mpo_vnode_check_setacl = biba_vnode_check_setacl, 3799 .mpo_vnode_check_setextattr = biba_vnode_check_setextattr, 3800 .mpo_vnode_check_setflags = biba_vnode_check_setflags, 3801 .mpo_vnode_check_setmode = biba_vnode_check_setmode, 3802 .mpo_vnode_check_setowner = biba_vnode_check_setowner, 3803 .mpo_vnode_check_setutimes = biba_vnode_check_setutimes, 3804 .mpo_vnode_check_stat = biba_vnode_check_stat, 3805 .mpo_vnode_check_unlink = biba_vnode_check_unlink, 3806 .mpo_vnode_check_write = biba_vnode_check_write, 3807 .mpo_vnode_create_extattr = biba_vnode_create_extattr, 3808 .mpo_vnode_copy_label = biba_copy_label, 3809 .mpo_vnode_destroy_label = biba_destroy_label, 3810 .mpo_vnode_externalize_label = biba_externalize_label, 3811 .mpo_vnode_init_label = biba_init_label, 3812 .mpo_vnode_internalize_label = biba_internalize_label, 3813 .mpo_vnode_relabel = biba_vnode_relabel, 3814 .mpo_vnode_setlabel_extattr = biba_vnode_setlabel_extattr, 3815 }; 3816 3817 MAC_POLICY_SET(&mac_biba_ops, mac_biba, "TrustedBSD MAC/Biba", 3818 MPC_LOADTIME_FLAG_NOTLATE, &biba_slot); 3819