ugidfw_system.c revision 145412
1/*- 2 * Copyright (c) 2005 Tom Rhodes 3 * Copyright (c) 1999-2002 Robert N. M. Watson 4 * Copyright (c) 2001-2005 Networks Associates Technology, Inc. 5 * All rights reserved. 6 * 7 * This software was developed by Robert Watson for the TrustedBSD Project. 8 * It was later enhanced by Tom Rhodes for the TrustedBSD Project. 9 * 10 * This software was developed for the FreeBSD Project in part by Network 11 * Associates Laboratories, the Security Research Division of Network 12 * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 ("CBOSS"), 13 * as part of the DARPA CHATS research program. 14 * 15 * Redistribution and use in source and binary forms, with or without 16 * modification, are permitted provided that the following conditions 17 * are met: 18 * 1. Redistributions of source code must retain the above copyright 19 * notice, this list of conditions and the following disclaimer. 20 * 2. Redistributions in binary form must reproduce the above copyright 21 * notice, this list of conditions and the following disclaimer in the 22 * documentation and/or other materials provided with the distribution. 23 * 24 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 25 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 26 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 27 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 28 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 29 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 30 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 31 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 32 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 33 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 34 * SUCH DAMAGE. 35 * 36 * $FreeBSD: head/sys/security/mac_bsdextended/mac_bsdextended.c 145412 2005-04-22 18:49:30Z trhodes $ 37 */ 38 39/* 40 * Developed by the TrustedBSD Project. 41 * "BSD Extended" MAC policy, allowing the administrator to impose 42 * mandatory rules regarding users and some system objects. 43 */ 44 45#include <sys/types.h> 46#include <sys/param.h> 47#include <sys/acl.h> 48#include <sys/conf.h> 49#include <sys/kernel.h> 50#include <sys/lock.h> 51#include <sys/mac.h> 52#include <sys/malloc.h> 53#include <sys/mount.h> 54#include <sys/mutex.h> 55#include <sys/proc.h> 56#include <sys/systm.h> 57#include <sys/sysproto.h> 58#include <sys/sysent.h> 59#include <sys/vnode.h> 60#include <sys/file.h> 61#include <sys/socket.h> 62#include <sys/socketvar.h> 63#include <sys/sysctl.h> 64#include <sys/syslog.h> 65 66#include <net/bpfdesc.h> 67#include <net/if.h> 68#include <net/if_types.h> 69#include <net/if_var.h> 70 71#include <vm/vm.h> 72 73#include <sys/mac_policy.h> 74 75#include <security/mac_bsdextended/mac_bsdextended.h> 76 77static struct mtx mac_bsdextended_mtx; 78 79SYSCTL_DECL(_security_mac); 80 81SYSCTL_NODE(_security_mac, OID_AUTO, bsdextended, CTLFLAG_RW, 0, 82 "TrustedBSD extended BSD MAC policy controls"); 83 84static int mac_bsdextended_enabled = 1; 85SYSCTL_INT(_security_mac_bsdextended, OID_AUTO, enabled, CTLFLAG_RW, 86 &mac_bsdextended_enabled, 0, "Enforce extended BSD policy"); 87TUNABLE_INT("security.mac.bsdextended.enabled", &mac_bsdextended_enabled); 88 89MALLOC_DEFINE(M_MACBSDEXTENDED, "mac_bsdextended", "BSD Extended MAC rule"); 90 91#define MAC_BSDEXTENDED_MAXRULES 250 92static struct mac_bsdextended_rule *rules[MAC_BSDEXTENDED_MAXRULES]; 93static int rule_count = 0; 94static int rule_slots = 0; 95 96SYSCTL_INT(_security_mac_bsdextended, OID_AUTO, rule_count, CTLFLAG_RD, 97 &rule_count, 0, "Number of defined rules\n"); 98SYSCTL_INT(_security_mac_bsdextended, OID_AUTO, rule_slots, CTLFLAG_RD, 99 &rule_slots, 0, "Number of used rule slots\n"); 100 101/* 102 * This is just used for logging purposes, eventually we would like 103 * to log much more then failed requests. 104 */ 105static int mac_bsdextended_logging; 106SYSCTL_INT(_security_mac_bsdextended, OID_AUTO, logging, CTLFLAG_RW, 107 &mac_bsdextended_logging, 0, "Log failed authorization requests"); 108 109/* 110 * This tunable is here for compatibility. It will allow the user 111 * to switch between the new mode (first rule matches) and the old 112 * functionality (all rules match). 113 */ 114static int 115mac_bsdextended_firstmatch_enabled; 116SYSCTL_INT(_security_mac_bsdextended, OID_AUTO, firstmatch_enabled, 117 CTLFLAG_RW, &mac_bsdextended_firstmatch_enabled, 1, 118 "Disable/enable match first rule functionality"); 119 120static int 121mac_bsdextended_rule_valid(struct mac_bsdextended_rule *rule) 122{ 123 124 if ((rule->mbr_subject.mbi_flags | MBI_BITS) != MBI_BITS) 125 return (EINVAL); 126 127 if ((rule->mbr_object.mbi_flags | MBI_BITS) != MBI_BITS) 128 return (EINVAL); 129 130 if ((rule->mbr_mode | MBI_ALLPERM) != MBI_ALLPERM) 131 return (EINVAL); 132 133 return (0); 134} 135 136static int 137sysctl_rule(SYSCTL_HANDLER_ARGS) 138{ 139 struct mac_bsdextended_rule temprule, *ruleptr; 140 u_int namelen; 141 int error, index, *name; 142 143 error = 0; 144 name = (int *)arg1; 145 namelen = arg2; 146 147 /* printf("bsdextended sysctl handler (namelen %d)\n", namelen); */ 148 149 if (namelen != 1) 150 return (EINVAL); 151 152 index = name[0]; 153 if (index > MAC_BSDEXTENDED_MAXRULES) 154 return (ENOENT); 155 156 ruleptr = NULL; 157 if (req->newptr && req->newlen != 0) { 158 error = SYSCTL_IN(req, &temprule, sizeof(temprule)); 159 if (error) 160 return (error); 161 MALLOC(ruleptr, struct mac_bsdextended_rule *, 162 sizeof(*ruleptr), M_MACBSDEXTENDED, M_WAITOK | M_ZERO); 163 } 164 165 mtx_lock(&mac_bsdextended_mtx); 166 167 if (req->oldptr) { 168 if (index < 0 || index > rule_slots + 1) { 169 error = ENOENT; 170 goto out; 171 } 172 if (rules[index] == NULL) { 173 error = ENOENT; 174 goto out; 175 } 176 temprule = *rules[index]; 177 } 178 179 if (req->newptr && req->newlen == 0) { 180 /* printf("deletion\n"); */ 181 KASSERT(ruleptr == NULL, ("sysctl_rule: ruleptr != NULL")); 182 ruleptr = rules[index]; 183 if (ruleptr == NULL) { 184 error = ENOENT; 185 goto out; 186 } 187 rule_count--; 188 rules[index] = NULL; 189 } else if (req->newptr) { 190 error = mac_bsdextended_rule_valid(&temprule); 191 if (error) 192 goto out; 193 194 if (rules[index] == NULL) { 195 /* printf("addition\n"); */ 196 *ruleptr = temprule; 197 rules[index] = ruleptr; 198 ruleptr = NULL; 199 if (index + 1 > rule_slots) 200 rule_slots = index + 1; 201 rule_count++; 202 } else { 203 /* printf("replacement\n"); */ 204 *rules[index] = temprule; 205 } 206 } 207 208out: 209 mtx_unlock(&mac_bsdextended_mtx); 210 if (ruleptr != NULL) 211 FREE(ruleptr, M_MACBSDEXTENDED); 212 if (req->oldptr && error == 0) { 213 error = SYSCTL_OUT(req, &temprule, sizeof(temprule)); 214 if (error) 215 return (error); 216 } 217 218 return (0); 219} 220 221SYSCTL_NODE(_security_mac_bsdextended, OID_AUTO, rules, 222 CTLFLAG_RW, sysctl_rule, "BSD extended MAC rules"); 223 224static void 225mac_bsdextended_init(struct mac_policy_conf *mpc) 226{ 227 228 /* Initialize ruleset lock. */ 229 mtx_init(&mac_bsdextended_mtx, "mac_bsdextended lock", NULL, MTX_DEF); 230 231 /* Register dynamic sysctl's for rules. */ 232} 233 234static void 235mac_bsdextended_destroy(struct mac_policy_conf *mpc) 236{ 237 238 /* Destroy ruleset lock. */ 239 mtx_destroy(&mac_bsdextended_mtx); 240 241 /* Tear down sysctls. */ 242} 243 244static int 245mac_bsdextended_rulecheck(struct mac_bsdextended_rule *rule, 246 struct ucred *cred, uid_t object_uid, gid_t object_gid, int acc_mode) 247{ 248 int match; 249 250 /* 251 * Is there a subject match? 252 */ 253 mtx_assert(&mac_bsdextended_mtx, MA_OWNED); 254 if (rule->mbr_subject.mbi_flags & MBI_UID_DEFINED) { 255 match = (rule->mbr_subject.mbi_uid == cred->cr_uid || 256 rule->mbr_subject.mbi_uid == cred->cr_ruid || 257 rule->mbr_subject.mbi_uid == cred->cr_svuid); 258 259 if (rule->mbr_subject.mbi_flags & MBI_NEGATED) 260 match = !match; 261 262 if (!match) 263 return (0); 264 } 265 266 if (rule->mbr_subject.mbi_flags & MBI_GID_DEFINED) { 267 match = (groupmember(rule->mbr_subject.mbi_gid, cred) || 268 rule->mbr_subject.mbi_gid == cred->cr_rgid || 269 rule->mbr_subject.mbi_gid == cred->cr_svgid); 270 271 if (rule->mbr_subject.mbi_flags & MBI_NEGATED) 272 match = !match; 273 274 if (!match) 275 return (0); 276 } 277 278 /* 279 * Is there an object match? 280 */ 281 if (rule->mbr_object.mbi_flags & MBI_UID_DEFINED) { 282 match = (rule->mbr_object.mbi_uid == object_uid); 283 284 if (rule->mbr_object.mbi_flags & MBI_NEGATED) 285 match = !match; 286 287 if (!match) 288 return (0); 289 } 290 291 if (rule->mbr_object.mbi_flags & MBI_GID_DEFINED) { 292 match = (rule->mbr_object.mbi_gid == object_gid); 293 294 if (rule->mbr_object.mbi_flags & MBI_NEGATED) 295 match = !match; 296 297 if (!match) 298 return (0); 299 } 300 301 /* 302 * Is the access permitted? 303 */ 304 if ((rule->mbr_mode & acc_mode) != acc_mode) { 305 if (mac_bsdextended_logging) 306 log(LOG_AUTHPRIV, "mac_bsdextended: %d:%d request %d" 307 " on %d:%d failed. \n", cred->cr_ruid, 308 cred->cr_rgid, acc_mode, object_uid, object_gid); 309 return (EACCES); /* Matching rule denies access */ 310 } 311 312 /* 313 * If the rule matched, permits access, and first match is enabled, 314 * return success. 315 */ 316 if (mac_bsdextended_firstmatch_enabled) 317 return (EJUSTRETURN); 318 else 319 return(0); 320} 321 322static int 323mac_bsdextended_check(struct ucred *cred, uid_t object_uid, gid_t object_gid, 324 int acc_mode) 325{ 326 int error, i; 327 328 if (suser_cred(cred, 0) == 0) 329 return (0); 330 331 mtx_lock(&mac_bsdextended_mtx); 332 for (i = 0; i < rule_slots; i++) { 333 if (rules[i] == NULL) 334 continue; 335 336 /* 337 * Since we do not separately handle append, map append to 338 * write. 339 */ 340 if (acc_mode & MBI_APPEND) { 341 acc_mode &= ~MBI_APPEND; 342 acc_mode |= MBI_WRITE; 343 } 344 345 error = mac_bsdextended_rulecheck(rules[i], cred, object_uid, 346 object_gid, acc_mode); 347 if (error == EJUSTRETURN) 348 break; 349 if (error) { 350 mtx_unlock(&mac_bsdextended_mtx); 351 return (error); 352 } 353 } 354 mtx_unlock(&mac_bsdextended_mtx); 355 return (0); 356} 357 358static int 359mac_bsdextended_check_system_swapon(struct ucred *cred, struct vnode *vp, 360 struct label *label) 361{ 362 struct vattr vap; 363 int error; 364 365 if (!mac_bsdextended_enabled) 366 return (0); 367 368 error = VOP_GETATTR(vp, &vap, cred, curthread); 369 if (error) 370 return (error); 371 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 372 MBI_WRITE)); 373} 374 375static int 376mac_bsdextended_check_vnode_access(struct ucred *cred, struct vnode *vp, 377 struct label *label, int acc_mode) 378{ 379 struct vattr vap; 380 int error; 381 382 if (!mac_bsdextended_enabled) 383 return (0); 384 385 error = VOP_GETATTR(vp, &vap, cred, curthread); 386 if (error) 387 return (error); 388 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, acc_mode)); 389} 390 391static int 392mac_bsdextended_check_vnode_chdir(struct ucred *cred, struct vnode *dvp, 393 struct label *dlabel) 394{ 395 struct vattr vap; 396 int error; 397 398 if (!mac_bsdextended_enabled) 399 return (0); 400 401 error = VOP_GETATTR(dvp, &vap, cred, curthread); 402 if (error) 403 return (error); 404 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 405 MBI_EXEC)); 406} 407 408static int 409mac_bsdextended_check_vnode_chroot(struct ucred *cred, struct vnode *dvp, 410 struct label *dlabel) 411{ 412 struct vattr vap; 413 int error; 414 415 if (!mac_bsdextended_enabled) 416 return (0); 417 418 error = VOP_GETATTR(dvp, &vap, cred, curthread); 419 if (error) 420 return (error); 421 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 422 MBI_EXEC)); 423} 424 425static int 426mac_bsdextended_check_create_vnode(struct ucred *cred, struct vnode *dvp, 427 struct label *dlabel, struct componentname *cnp, struct vattr *vap) 428{ 429 struct vattr dvap; 430 int error; 431 432 if (!mac_bsdextended_enabled) 433 return (0); 434 435 error = VOP_GETATTR(dvp, &dvap, cred, curthread); 436 if (error) 437 return (error); 438 return (mac_bsdextended_check(cred, dvap.va_uid, dvap.va_gid, 439 MBI_WRITE)); 440} 441 442static int 443mac_bsdextended_check_vnode_delete(struct ucred *cred, struct vnode *dvp, 444 struct label *dlabel, struct vnode *vp, struct label *label, 445 struct componentname *cnp) 446{ 447 struct vattr vap; 448 int error; 449 450 if (!mac_bsdextended_enabled) 451 return (0); 452 453 error = VOP_GETATTR(dvp, &vap, cred, curthread); 454 if (error) 455 return (error); 456 error = mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 457 MBI_WRITE); 458 if (error) 459 return (error); 460 461 error = VOP_GETATTR(vp, &vap, cred, curthread); 462 if (error) 463 return (error); 464 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 465 MBI_WRITE)); 466} 467 468static int 469mac_bsdextended_check_vnode_deleteacl(struct ucred *cred, struct vnode *vp, 470 struct label *label, acl_type_t type) 471{ 472 struct vattr vap; 473 int error; 474 475 if (!mac_bsdextended_enabled) 476 return (0); 477 478 error = VOP_GETATTR(vp, &vap, cred, curthread); 479 if (error) 480 return (error); 481 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 482 MBI_ADMIN)); 483} 484 485static int 486mac_bsdextended_check_vnode_deleteextattr(struct ucred *cred, struct vnode *vp, 487 struct label *label, int attrnamespace, const char *name) 488{ 489 struct vattr vap; 490 int error; 491 492 if (!mac_bsdextended_enabled) 493 return (0); 494 495 error = VOP_GETATTR(vp, &vap, cred, curthread); 496 if (error) 497 return (error); 498 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 499 MBI_WRITE)); 500} 501 502static int 503mac_bsdextended_check_vnode_exec(struct ucred *cred, struct vnode *vp, 504 struct label *label, struct image_params *imgp, 505 struct label *execlabel) 506{ 507 struct vattr vap; 508 int error; 509 510 if (!mac_bsdextended_enabled) 511 return (0); 512 513 error = VOP_GETATTR(vp, &vap, cred, curthread); 514 if (error) 515 return (error); 516 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 517 MBI_READ|MBI_EXEC)); 518} 519 520static int 521mac_bsdextended_check_vnode_getacl(struct ucred *cred, struct vnode *vp, 522 struct label *label, acl_type_t type) 523{ 524 struct vattr vap; 525 int error; 526 527 if (!mac_bsdextended_enabled) 528 return (0); 529 530 error = VOP_GETATTR(vp, &vap, cred, curthread); 531 if (error) 532 return (error); 533 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 534 MBI_STAT)); 535} 536 537static int 538mac_bsdextended_check_vnode_getextattr(struct ucred *cred, struct vnode *vp, 539 struct label *label, int attrnamespace, const char *name, struct uio *uio) 540{ 541 struct vattr vap; 542 int error; 543 544 if (!mac_bsdextended_enabled) 545 return (0); 546 547 error = VOP_GETATTR(vp, &vap, cred, curthread); 548 if (error) 549 return (error); 550 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 551 MBI_READ)); 552} 553 554static int 555mac_bsdextended_check_vnode_link(struct ucred *cred, struct vnode *dvp, 556 struct label *dlabel, struct vnode *vp, struct label *label, 557 struct componentname *cnp) 558{ 559 struct vattr vap; 560 int error; 561 562 if (!mac_bsdextended_enabled) 563 return (0); 564 565 error = VOP_GETATTR(dvp, &vap, cred, curthread); 566 if (error) 567 return (error); 568 error = mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 569 MBI_WRITE); 570 if (error) 571 return (error); 572 573 error = VOP_GETATTR(vp, &vap, cred, curthread); 574 if (error) 575 return (error); 576 error = mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 577 MBI_WRITE); 578 if (error) 579 return (error); 580 return (0); 581} 582 583static int 584mac_bsdextended_check_vnode_listextattr(struct ucred *cred, struct vnode *vp, 585 struct label *label, int attrnamespace) 586{ 587 struct vattr vap; 588 int error; 589 590 if (!mac_bsdextended_enabled) 591 return (0); 592 593 error = VOP_GETATTR(vp, &vap, cred, curthread); 594 if (error) 595 return (error); 596 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 597 MBI_READ)); 598} 599 600static int 601mac_bsdextended_check_vnode_lookup(struct ucred *cred, struct vnode *dvp, 602 struct label *dlabel, struct componentname *cnp) 603{ 604 struct vattr vap; 605 int error; 606 607 if (!mac_bsdextended_enabled) 608 return (0); 609 610 error = VOP_GETATTR(dvp, &vap, cred, curthread); 611 if (error) 612 return (error); 613 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 614 MBI_EXEC)); 615} 616 617static int 618mac_bsdextended_check_vnode_open(struct ucred *cred, struct vnode *vp, 619 struct label *filelabel, int acc_mode) 620{ 621 struct vattr vap; 622 int error; 623 624 if (!mac_bsdextended_enabled) 625 return (0); 626 627 error = VOP_GETATTR(vp, &vap, cred, curthread); 628 if (error) 629 return (error); 630 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, acc_mode)); 631} 632 633static int 634mac_bsdextended_check_vnode_readdir(struct ucred *cred, struct vnode *dvp, 635 struct label *dlabel) 636{ 637 struct vattr vap; 638 int error; 639 640 if (!mac_bsdextended_enabled) 641 return (0); 642 643 error = VOP_GETATTR(dvp, &vap, cred, curthread); 644 if (error) 645 return (error); 646 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 647 MBI_READ)); 648} 649 650static int 651mac_bsdextended_check_vnode_readdlink(struct ucred *cred, struct vnode *vp, 652 struct label *label) 653{ 654 struct vattr vap; 655 int error; 656 657 if (!mac_bsdextended_enabled) 658 return (0); 659 660 error = VOP_GETATTR(vp, &vap, cred, curthread); 661 if (error) 662 return (error); 663 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 664 MBI_READ)); 665} 666 667static int 668mac_bsdextended_check_vnode_rename_from(struct ucred *cred, struct vnode *dvp, 669 struct label *dlabel, struct vnode *vp, struct label *label, 670 struct componentname *cnp) 671{ 672 struct vattr vap; 673 int error; 674 675 if (!mac_bsdextended_enabled) 676 return (0); 677 678 error = VOP_GETATTR(dvp, &vap, cred, curthread); 679 if (error) 680 return (error); 681 error = mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 682 MBI_WRITE); 683 if (error) 684 return (error); 685 error = VOP_GETATTR(vp, &vap, cred, curthread); 686 if (error) 687 return (error); 688 error = mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 689 MBI_WRITE); 690 691 return (error); 692} 693 694static int 695mac_bsdextended_check_vnode_rename_to(struct ucred *cred, struct vnode *dvp, 696 struct label *dlabel, struct vnode *vp, struct label *label, int samedir, 697 struct componentname *cnp) 698{ 699 struct vattr vap; 700 int error; 701 702 if (!mac_bsdextended_enabled) 703 return (0); 704 705 error = VOP_GETATTR(dvp, &vap, cred, curthread); 706 if (error) 707 return (error); 708 error = mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 709 MBI_WRITE); 710 if (error) 711 return (error); 712 713 if (vp != NULL) { 714 error = VOP_GETATTR(vp, &vap, cred, curthread); 715 if (error) 716 return (error); 717 error = mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 718 MBI_WRITE); 719 } 720 721 return (error); 722} 723 724static int 725mac_bsdextended_check_vnode_revoke(struct ucred *cred, struct vnode *vp, 726 struct label *label) 727{ 728 struct vattr vap; 729 int error; 730 731 if (!mac_bsdextended_enabled) 732 return (0); 733 734 error = VOP_GETATTR(vp, &vap, cred, curthread); 735 if (error) 736 return (error); 737 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 738 MBI_ADMIN)); 739} 740 741static int 742mac_bsdextended_check_setacl_vnode(struct ucred *cred, struct vnode *vp, 743 struct label *label, acl_type_t type, struct acl *acl) 744{ 745 struct vattr vap; 746 int error; 747 748 if (!mac_bsdextended_enabled) 749 return (0); 750 751 error = VOP_GETATTR(vp, &vap, cred, curthread); 752 if (error) 753 return (error); 754 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 755 MBI_ADMIN)); 756} 757 758static int 759mac_bsdextended_check_vnode_setextattr(struct ucred *cred, struct vnode *vp, 760 struct label *label, int attrnamespace, const char *name, struct uio *uio) 761{ 762 struct vattr vap; 763 int error; 764 765 if (!mac_bsdextended_enabled) 766 return (0); 767 768 error = VOP_GETATTR(vp, &vap, cred, curthread); 769 if (error) 770 return (error); 771 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 772 MBI_WRITE)); 773} 774 775static int 776mac_bsdextended_check_vnode_setflags(struct ucred *cred, struct vnode *vp, 777 struct label *label, u_long flags) 778{ 779 struct vattr vap; 780 int error; 781 782 if (!mac_bsdextended_enabled) 783 return (0); 784 785 error = VOP_GETATTR(vp, &vap, cred, curthread); 786 if (error) 787 return (error); 788 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 789 MBI_ADMIN)); 790} 791 792static int 793mac_bsdextended_check_vnode_setmode(struct ucred *cred, struct vnode *vp, 794 struct label *label, mode_t mode) 795{ 796 struct vattr vap; 797 int error; 798 799 if (!mac_bsdextended_enabled) 800 return (0); 801 802 error = VOP_GETATTR(vp, &vap, cred, curthread); 803 if (error) 804 return (error); 805 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 806 MBI_ADMIN)); 807} 808 809static int 810mac_bsdextended_check_vnode_setowner(struct ucred *cred, struct vnode *vp, 811 struct label *label, uid_t uid, gid_t gid) 812{ 813 struct vattr vap; 814 int error; 815 816 if (!mac_bsdextended_enabled) 817 return (0); 818 819 error = VOP_GETATTR(vp, &vap, cred, curthread); 820 if (error) 821 return (error); 822 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 823 MBI_ADMIN)); 824} 825 826static int 827mac_bsdextended_check_vnode_setutimes(struct ucred *cred, struct vnode *vp, 828 struct label *label, struct timespec atime, struct timespec utime) 829{ 830 struct vattr vap; 831 int error; 832 833 if (!mac_bsdextended_enabled) 834 return (0); 835 836 error = VOP_GETATTR(vp, &vap, cred, curthread); 837 if (error) 838 return (error); 839 return (mac_bsdextended_check(cred, vap.va_uid, vap.va_gid, 840 MBI_ADMIN)); 841} 842 843static int 844mac_bsdextended_check_vnode_stat(struct ucred *active_cred, 845 struct ucred *file_cred, struct vnode *vp, struct label *label) 846{ 847 struct vattr vap; 848 int error; 849 850 if (!mac_bsdextended_enabled) 851 return (0); 852 853 error = VOP_GETATTR(vp, &vap, active_cred, curthread); 854 if (error) 855 return (error); 856 return (mac_bsdextended_check(active_cred, vap.va_uid, vap.va_gid, 857 MBI_STAT)); 858} 859 860static struct mac_policy_ops mac_bsdextended_ops = 861{ 862 .mpo_destroy = mac_bsdextended_destroy, 863 .mpo_init = mac_bsdextended_init, 864 .mpo_check_system_swapon = mac_bsdextended_check_system_swapon, 865 .mpo_check_vnode_access = mac_bsdextended_check_vnode_access, 866 .mpo_check_vnode_chdir = mac_bsdextended_check_vnode_chdir, 867 .mpo_check_vnode_chroot = mac_bsdextended_check_vnode_chroot, 868 .mpo_check_vnode_create = mac_bsdextended_check_create_vnode, 869 .mpo_check_vnode_delete = mac_bsdextended_check_vnode_delete, 870 .mpo_check_vnode_deleteacl = mac_bsdextended_check_vnode_deleteacl, 871 .mpo_check_vnode_deleteextattr = mac_bsdextended_check_vnode_deleteextattr, 872 .mpo_check_vnode_exec = mac_bsdextended_check_vnode_exec, 873 .mpo_check_vnode_getacl = mac_bsdextended_check_vnode_getacl, 874 .mpo_check_vnode_getextattr = mac_bsdextended_check_vnode_getextattr, 875 .mpo_check_vnode_link = mac_bsdextended_check_vnode_link, 876 .mpo_check_vnode_listextattr = mac_bsdextended_check_vnode_listextattr, 877 .mpo_check_vnode_lookup = mac_bsdextended_check_vnode_lookup, 878 .mpo_check_vnode_open = mac_bsdextended_check_vnode_open, 879 .mpo_check_vnode_readdir = mac_bsdextended_check_vnode_readdir, 880 .mpo_check_vnode_readlink = mac_bsdextended_check_vnode_readdlink, 881 .mpo_check_vnode_rename_from = mac_bsdextended_check_vnode_rename_from, 882 .mpo_check_vnode_rename_to = mac_bsdextended_check_vnode_rename_to, 883 .mpo_check_vnode_revoke = mac_bsdextended_check_vnode_revoke, 884 .mpo_check_vnode_setacl = mac_bsdextended_check_setacl_vnode, 885 .mpo_check_vnode_setextattr = mac_bsdextended_check_vnode_setextattr, 886 .mpo_check_vnode_setflags = mac_bsdextended_check_vnode_setflags, 887 .mpo_check_vnode_setmode = mac_bsdextended_check_vnode_setmode, 888 .mpo_check_vnode_setowner = mac_bsdextended_check_vnode_setowner, 889 .mpo_check_vnode_setutimes = mac_bsdextended_check_vnode_setutimes, 890 .mpo_check_vnode_stat = mac_bsdextended_check_vnode_stat, 891}; 892 893MAC_POLICY_SET(&mac_bsdextended_ops, mac_bsdextended, 894 "TrustedBSD MAC/BSD Extended", MPC_LOADTIME_FLAG_UNLOADOK, NULL); 895