1 /* 2 * Copyright (c) 2004,2009 The DragonFly Project. All rights reserved. 3 * 4 * This code is derived from software contributed to The DragonFly Project 5 * by Matthew Dillon <dillon@backplane.com> 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions 9 * are met: 10 * 11 * 1. Redistributions of source code must retain the above copyright 12 * notice, this list of conditions and the following disclaimer. 13 * 2. Redistributions in binary form must reproduce the above copyright 14 * notice, this list of conditions and the following disclaimer in 15 * the documentation and/or other materials provided with the 16 * distribution. 17 * 3. Neither the name of The DragonFly Project nor the names of its 18 * contributors may be used to endorse or promote products derived 19 * from this software without specific, prior written permission. 20 * 21 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 22 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 23 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 24 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE 25 * COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 26 * INCIDENTAL, SPECIAL, EXEMPLARY OR CONSEQUENTIAL DAMAGES (INCLUDING, 27 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 28 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED 29 * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 30 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT 31 * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 32 * SUCH DAMAGE. 33 */ 34 /* 35 * Implement vnode ops wrappers. All vnode ops are wrapped through 36 * these functions. 37 * 38 * These wrappers are responsible for hanlding all MPSAFE issues related 39 * to a vnode operation. 40 */ 41 42 #include <sys/param.h> 43 #include <sys/systm.h> 44 #include <sys/buf.h> 45 #include <sys/conf.h> 46 #include <sys/dirent.h> 47 #include <sys/domain.h> 48 #include <sys/eventhandler.h> 49 #include <sys/fcntl.h> 50 #include <sys/kernel.h> 51 #include <sys/kthread.h> 52 #include <sys/malloc.h> 53 #include <sys/mbuf.h> 54 #include <sys/mount.h> 55 #include <sys/proc.h> 56 #include <sys/namei.h> 57 #include <sys/reboot.h> 58 #include <sys/socket.h> 59 #include <sys/stat.h> 60 #include <sys/sysctl.h> 61 #include <sys/syslog.h> 62 #include <sys/vmmeter.h> 63 #include <sys/vnode.h> 64 #include <sys/vfsops.h> 65 #include <sys/sysmsg.h> 66 #include <sys/vfs_quota.h> 67 68 #include <machine/limits.h> 69 70 #include <vm/vm.h> 71 #include <vm/vm_object.h> 72 #include <vm/vm_extern.h> 73 #include <vm/vm_kern.h> 74 #include <vm/pmap.h> 75 #include <vm/vm_map.h> 76 #include <vm/vm_page.h> 77 #include <vm/vm_pager.h> 78 #include <vm/vnode_pager.h> 79 #include <vm/vm_zone.h> 80 81 #include <sys/buf2.h> 82 #include <sys/mplock2.h> 83 84 #define VDESCNAME(name) __CONCAT(__CONCAT(vop_,name),_desc) 85 86 #define VNODEOP_DESC_INIT(name) \ 87 struct syslink_desc VDESCNAME(name) = { \ 88 __offsetof(struct vop_ops, __CONCAT(vop_, name)), \ 89 #name } 90 91 VNODEOP_DESC_INIT(default); 92 VNODEOP_DESC_INIT(old_lookup); 93 VNODEOP_DESC_INIT(old_create); 94 VNODEOP_DESC_INIT(old_whiteout); 95 VNODEOP_DESC_INIT(old_mknod); 96 VNODEOP_DESC_INIT(open); 97 VNODEOP_DESC_INIT(close); 98 VNODEOP_DESC_INIT(access); 99 VNODEOP_DESC_INIT(getattr); 100 VNODEOP_DESC_INIT(getattr_lite); 101 VNODEOP_DESC_INIT(setattr); 102 VNODEOP_DESC_INIT(read); 103 VNODEOP_DESC_INIT(write); 104 VNODEOP_DESC_INIT(ioctl); 105 VNODEOP_DESC_INIT(poll); 106 VNODEOP_DESC_INIT(kqfilter); 107 VNODEOP_DESC_INIT(mmap); 108 VNODEOP_DESC_INIT(fsync); 109 VNODEOP_DESC_INIT(old_remove); 110 VNODEOP_DESC_INIT(old_link); 111 VNODEOP_DESC_INIT(old_rename); 112 113 VNODEOP_DESC_INIT(old_mkdir); 114 VNODEOP_DESC_INIT(old_rmdir); 115 VNODEOP_DESC_INIT(old_symlink); 116 VNODEOP_DESC_INIT(readdir); 117 VNODEOP_DESC_INIT(readlink); 118 VNODEOP_DESC_INIT(inactive); 119 VNODEOP_DESC_INIT(reclaim); 120 VNODEOP_DESC_INIT(bmap); 121 VNODEOP_DESC_INIT(strategy); 122 VNODEOP_DESC_INIT(print); 123 VNODEOP_DESC_INIT(pathconf); 124 VNODEOP_DESC_INIT(advlock); 125 VNODEOP_DESC_INIT(balloc); 126 VNODEOP_DESC_INIT(reallocblks); 127 VNODEOP_DESC_INIT(getpages); 128 VNODEOP_DESC_INIT(putpages); 129 VNODEOP_DESC_INIT(freeblks); 130 VNODEOP_DESC_INIT(getacl); 131 VNODEOP_DESC_INIT(setacl); 132 VNODEOP_DESC_INIT(aclcheck); 133 VNODEOP_DESC_INIT(getextattr); 134 VNODEOP_DESC_INIT(setextattr); 135 VNODEOP_DESC_INIT(mountctl); 136 VNODEOP_DESC_INIT(markatime); 137 VNODEOP_DESC_INIT(allocate); 138 139 VNODEOP_DESC_INIT(nresolve); 140 VNODEOP_DESC_INIT(nlookupdotdot); 141 VNODEOP_DESC_INIT(ncreate); 142 VNODEOP_DESC_INIT(nmkdir); 143 VNODEOP_DESC_INIT(nmknod); 144 VNODEOP_DESC_INIT(nlink); 145 VNODEOP_DESC_INIT(nsymlink); 146 VNODEOP_DESC_INIT(nwhiteout); 147 VNODEOP_DESC_INIT(nremove); 148 VNODEOP_DESC_INIT(nrmdir); 149 VNODEOP_DESC_INIT(nrename); 150 151 #define DO_OPS(ops, error, ap, vop_field) \ 152 error = ops->vop_field(ap) 153 154 /************************************************************************ 155 * PRIMARY HIGH LEVEL VNODE OPERATIONS CALLS * 156 ************************************************************************ 157 * 158 * These procedures are called directly from the kernel and/or fileops 159 * code to perform file/device operations on the system. 160 * 161 * NOTE: The old namespace api functions such as vop_rename() are no 162 * longer available for general use and have been renamed to 163 * vop_old_*(). Only the code in vfs_default.c is allowed to call 164 * those ops. 165 * 166 * NOTE: The VFS_MPLOCK() macro handle mounts which do not set MNTK_MPSAFE. 167 * 168 * MPSAFE 169 */ 170 171 int 172 vop_old_lookup(struct vop_ops *ops, struct vnode *dvp, 173 struct vnode **vpp, struct componentname *cnp) 174 { 175 struct vop_old_lookup_args ap; 176 VFS_MPLOCK_DECLARE; 177 int error; 178 179 ap.a_head.a_desc = &vop_old_lookup_desc; 180 ap.a_head.a_ops = ops; 181 ap.a_dvp = dvp; 182 ap.a_vpp = vpp; 183 ap.a_cnp = cnp; 184 VFS_MPLOCK(dvp->v_mount); 185 DO_OPS(ops, error, &ap, vop_old_lookup); 186 VFS_MPUNLOCK(); 187 188 return(error); 189 } 190 191 /* 192 * MPSAFE 193 */ 194 int 195 vop_old_create(struct vop_ops *ops, struct vnode *dvp, 196 struct vnode **vpp, struct componentname *cnp, struct vattr *vap) 197 { 198 struct vop_old_create_args ap; 199 VFS_MPLOCK_DECLARE; 200 int error; 201 202 ap.a_head.a_desc = &vop_old_create_desc; 203 ap.a_head.a_ops = ops; 204 ap.a_dvp = dvp; 205 ap.a_vpp = vpp; 206 ap.a_cnp = cnp; 207 ap.a_vap = vap; 208 209 VFS_MPLOCK(dvp->v_mount); 210 DO_OPS(ops, error, &ap, vop_old_create); 211 VFS_MPUNLOCK(); 212 213 return(error); 214 } 215 216 /* 217 * MPSAFE 218 */ 219 int 220 vop_old_whiteout(struct vop_ops *ops, struct vnode *dvp, 221 struct componentname *cnp, int flags) 222 { 223 struct vop_old_whiteout_args ap; 224 VFS_MPLOCK_DECLARE; 225 int error; 226 227 ap.a_head.a_desc = &vop_old_whiteout_desc; 228 ap.a_head.a_ops = ops; 229 ap.a_dvp = dvp; 230 ap.a_cnp = cnp; 231 ap.a_flags = flags; 232 233 VFS_MPLOCK(dvp->v_mount); 234 DO_OPS(ops, error, &ap, vop_old_whiteout); 235 VFS_MPUNLOCK(); 236 237 return(error); 238 } 239 240 /* 241 * MPSAFE 242 */ 243 int 244 vop_old_mknod(struct vop_ops *ops, struct vnode *dvp, 245 struct vnode **vpp, struct componentname *cnp, struct vattr *vap) 246 { 247 struct vop_old_mknod_args ap; 248 VFS_MPLOCK_DECLARE; 249 int error; 250 251 ap.a_head.a_desc = &vop_old_mknod_desc; 252 ap.a_head.a_ops = ops; 253 ap.a_dvp = dvp; 254 ap.a_vpp = vpp; 255 ap.a_cnp = cnp; 256 ap.a_vap = vap; 257 258 VFS_MPLOCK(dvp->v_mount); 259 DO_OPS(ops, error, &ap, vop_old_mknod); 260 VFS_MPUNLOCK(); 261 262 return(error); 263 } 264 265 /* 266 * NOTE: VAGE is always cleared when calling VOP_OPEN(). 267 */ 268 int 269 vop_open(struct vop_ops *ops, struct vnode *vp, int mode, struct ucred *cred, 270 struct file **fpp) 271 { 272 struct vop_open_args ap; 273 VFS_MPLOCK_DECLARE; 274 int error; 275 276 /* 277 * Decrement 3-2-1-0. Does not decrement beyond 0 278 */ 279 if (vp->v_flag & VAGE0) { 280 vclrflags(vp, VAGE0); 281 } else if (vp->v_flag & VAGE1) { 282 vclrflags(vp, VAGE1); 283 vsetflags(vp, VAGE0); 284 } 285 286 ap.a_head.a_desc = &vop_open_desc; 287 ap.a_head.a_ops = ops; 288 ap.a_vp = vp; 289 ap.a_fpp = fpp; 290 ap.a_mode = mode; 291 ap.a_cred = cred; 292 293 VFS_MPLOCK(vp->v_mount); 294 DO_OPS(ops, error, &ap, vop_open); 295 VFS_MPUNLOCK(); 296 297 return(error); 298 } 299 300 /* 301 * MPSAFE 302 */ 303 int 304 vop_close(struct vop_ops *ops, struct vnode *vp, int fflag, struct file *fp) 305 { 306 struct vop_close_args ap; 307 VFS_MPLOCK_DECLARE; 308 int error; 309 310 ap.a_head.a_desc = &vop_close_desc; 311 ap.a_head.a_ops = ops; 312 ap.a_vp = vp; 313 ap.a_fp = fp; 314 ap.a_fflag = fflag; 315 316 VFS_MPLOCK(vp->v_mount); 317 DO_OPS(ops, error, &ap, vop_close); 318 VFS_MPUNLOCK(); 319 320 return(error); 321 } 322 323 /* 324 * MPSAFE 325 */ 326 int 327 vop_access(struct vop_ops *ops, struct vnode *vp, int mode, int flags, 328 struct ucred *cred) 329 { 330 struct vop_access_args ap; 331 VFS_MPLOCK_DECLARE; 332 int error; 333 334 ap.a_head.a_desc = &vop_access_desc; 335 ap.a_head.a_ops = ops; 336 ap.a_vp = vp; 337 ap.a_mode = mode; 338 ap.a_flags = flags; 339 ap.a_cred = cred; 340 341 VFS_MPLOCK(vp->v_mount); 342 DO_OPS(ops, error, &ap, vop_access); 343 VFS_MPUNLOCK(); 344 345 return(error); 346 } 347 348 /* 349 * MPSAFE 350 */ 351 int 352 vop_getattr(struct vop_ops *ops, struct vnode *vp, struct vattr *vap, 353 struct file *fp) 354 { 355 struct vop_getattr_args ap; 356 VFS_MPLOCK_DECLARE; 357 int error; 358 359 ap.a_head.a_desc = &vop_getattr_desc; 360 ap.a_head.a_ops = ops; 361 ap.a_vp = vp; 362 ap.a_vap = vap; 363 ap.a_fp = fp; 364 365 VFS_MPLOCK_FLAG(vp->v_mount, MNTK_GA_MPSAFE); 366 DO_OPS(ops, error, &ap, vop_getattr); 367 VFS_MPUNLOCK(); 368 369 return(error); 370 } 371 372 /* 373 * MPSAFE 374 */ 375 int 376 vop_getattr_lite(struct vop_ops *ops, struct vnode *vp, struct vattr_lite *lvap) 377 { 378 struct vop_getattr_lite_args ap; 379 VFS_MPLOCK_DECLARE; 380 int error; 381 382 ap.a_head.a_desc = &vop_getattr_lite_desc; 383 ap.a_head.a_ops = ops; 384 ap.a_vp = vp; 385 ap.a_lvap = lvap; 386 ap.a_fp = NULL; 387 388 VFS_MPLOCK_FLAG(vp->v_mount, MNTK_GA_MPSAFE); 389 DO_OPS(ops, error, &ap, vop_getattr_lite); 390 VFS_MPUNLOCK(); 391 392 return(error); 393 } 394 395 /* 396 * MPSAFE 397 */ 398 int 399 vop_setattr(struct vop_ops *ops, struct vnode *vp, struct vattr *vap, 400 struct ucred *cred, struct file *fp) 401 { 402 struct vop_setattr_args ap; 403 VFS_MPLOCK_DECLARE; 404 int error; 405 406 ap.a_head.a_desc = &vop_setattr_desc; 407 ap.a_head.a_ops = ops; 408 ap.a_vp = vp; 409 ap.a_vap = vap; 410 ap.a_cred = cred; 411 ap.a_fp = fp; 412 413 VFS_MPLOCK(vp->v_mount); 414 DO_OPS(ops, error, &ap, vop_setattr); 415 VFS_MPUNLOCK(); 416 417 return(error); 418 } 419 420 /* 421 * MPSAFE 422 */ 423 int 424 vop_read(struct vop_ops *ops, struct vnode *vp, struct uio *uio, int ioflag, 425 struct ucred *cred, struct file *fp) 426 { 427 struct vop_read_args ap; 428 VFS_MPLOCK_DECLARE; 429 int error; 430 431 ap.a_head.a_desc = &vop_read_desc; 432 ap.a_head.a_ops = ops; 433 ap.a_vp = vp; 434 ap.a_uio = uio; 435 ap.a_ioflag = ioflag; 436 ap.a_cred = cred; 437 ap.a_fp = fp; 438 439 VFS_MPLOCK_FLAG(vp->v_mount, MNTK_RD_MPSAFE); 440 DO_OPS(ops, error, &ap, vop_read); 441 VFS_MPUNLOCK(); 442 443 return(error); 444 } 445 446 /* 447 * MPSAFE 448 */ 449 int 450 vop_write(struct vop_ops *ops, struct vnode *vp, struct uio *uio, int ioflag, 451 struct ucred *cred, struct file *fp) 452 { 453 struct vop_write_args ap; 454 VFS_MPLOCK_DECLARE; 455 int error, do_accounting = 0; 456 struct vattr va; 457 uint64_t size_before=0, size_after=0; 458 struct mount *mp; 459 uint64_t offset, delta; 460 461 ap.a_head.a_desc = &vop_write_desc; 462 ap.a_head.a_ops = ops; 463 ap.a_vp = vp; 464 ap.a_uio = uio; 465 ap.a_ioflag = ioflag; 466 ap.a_cred = cred; 467 ap.a_fp = fp; 468 469 /* is this a regular vnode ? */ 470 VFS_MPLOCK_FLAG(vp->v_mount, MNTK_WR_MPSAFE); 471 if (vfs_quota_enabled && (vp->v_type == VREG)) { 472 if ((error = VOP_GETATTR(vp, &va)) != 0) 473 goto done; 474 size_before = va.va_size; 475 /* this file may already have been removed */ 476 if (va.va_nlink > 0) 477 do_accounting = 1; 478 479 offset = uio->uio_offset; 480 if (ioflag & IO_APPEND) 481 offset = size_before; 482 size_after = offset + uio->uio_resid; 483 if (size_after < size_before) 484 size_after = size_before; 485 delta = size_after - size_before; 486 mp = vq_vptomp(vp); 487 /* QUOTA CHECK */ 488 if (!vq_write_ok(mp, va.va_uid, va.va_gid, delta)) { 489 error = EDQUOT; 490 goto done; 491 } 492 } 493 DO_OPS(ops, error, &ap, vop_write); 494 if ((error == 0) && do_accounting) { 495 VFS_ACCOUNT(mp, va.va_uid, va.va_gid, size_after - size_before); 496 } 497 done: 498 VFS_MPUNLOCK(); 499 500 return(error); 501 } 502 503 /* 504 * MPSAFE 505 */ 506 int 507 vop_ioctl(struct vop_ops *ops, struct vnode *vp, u_long command, caddr_t data, 508 int fflag, struct ucred *cred, struct sysmsg *msg) 509 { 510 struct vop_ioctl_args ap; 511 VFS_MPLOCK_DECLARE; 512 int error; 513 514 ap.a_head.a_desc = &vop_ioctl_desc; 515 ap.a_head.a_ops = ops; 516 ap.a_vp = vp; 517 ap.a_command = command; 518 ap.a_data = data; 519 ap.a_fflag = fflag; 520 ap.a_cred = cred; 521 ap.a_sysmsg = msg; 522 523 VFS_MPLOCK(vp->v_mount); 524 DO_OPS(ops, error, &ap, vop_ioctl); 525 VFS_MPUNLOCK(); 526 527 return(error); 528 } 529 530 /* 531 * MPSAFE 532 */ 533 int 534 vop_poll(struct vop_ops *ops, struct vnode *vp, int events, struct ucred *cred) 535 { 536 struct vop_poll_args ap; 537 VFS_MPLOCK_DECLARE; 538 int error; 539 540 ap.a_head.a_desc = &vop_poll_desc; 541 ap.a_head.a_ops = ops; 542 ap.a_vp = vp; 543 ap.a_events = events; 544 ap.a_cred = cred; 545 546 VFS_MPLOCK(vp->v_mount); 547 DO_OPS(ops, error, &ap, vop_poll); 548 VFS_MPUNLOCK(); 549 550 return(error); 551 } 552 553 /* 554 * MPSAFE 555 */ 556 int 557 vop_kqfilter(struct vop_ops *ops, struct vnode *vp, struct knote *kn) 558 { 559 struct vop_kqfilter_args ap; 560 VFS_MPLOCK_DECLARE; 561 int error; 562 563 ap.a_head.a_desc = &vop_kqfilter_desc; 564 ap.a_head.a_ops = ops; 565 ap.a_vp = vp; 566 ap.a_kn = kn; 567 568 VFS_MPLOCK(vp->v_mount); 569 DO_OPS(ops, error, &ap, vop_kqfilter); 570 VFS_MPUNLOCK(); 571 572 return(error); 573 } 574 575 /* 576 * MPSAFE 577 */ 578 int 579 vop_mmap(struct vop_ops *ops, struct vnode *vp, int fflags, struct ucred *cred) 580 { 581 struct vop_mmap_args ap; 582 VFS_MPLOCK_DECLARE; 583 int error; 584 585 ap.a_head.a_desc = &vop_mmap_desc; 586 ap.a_head.a_ops = ops; 587 ap.a_vp = vp; 588 ap.a_fflags = fflags; 589 ap.a_cred = cred; 590 591 VFS_MPLOCK(vp->v_mount); 592 DO_OPS(ops, error, &ap, vop_mmap); 593 VFS_MPUNLOCK(); 594 595 return(error); 596 } 597 598 /* 599 * MPSAFE 600 */ 601 int 602 vop_fsync(struct vop_ops *ops, struct vnode *vp, int waitfor, int flags, 603 struct file *fp) 604 { 605 struct vop_fsync_args ap; 606 VFS_MPLOCK_DECLARE; 607 int error; 608 609 ap.a_head.a_desc = &vop_fsync_desc; 610 ap.a_head.a_ops = ops; 611 ap.a_vp = vp; 612 ap.a_waitfor = waitfor; 613 ap.a_flags = flags; 614 ap.a_fp = fp; 615 616 VFS_MPLOCK(vp->v_mount); 617 DO_OPS(ops, error, &ap, vop_fsync); 618 VFS_MPUNLOCK(); 619 620 return(error); 621 } 622 623 /* 624 * MPSAFE 625 */ 626 int 627 vop_old_remove(struct vop_ops *ops, struct vnode *dvp, 628 struct vnode *vp, struct componentname *cnp) 629 { 630 struct vop_old_remove_args ap; 631 VFS_MPLOCK_DECLARE; 632 int error; 633 634 ap.a_head.a_desc = &vop_old_remove_desc; 635 ap.a_head.a_ops = ops; 636 ap.a_dvp = dvp; 637 ap.a_vp = vp; 638 ap.a_cnp = cnp; 639 640 VFS_MPLOCK(dvp->v_mount); 641 DO_OPS(ops, error, &ap, vop_old_remove); 642 VFS_MPUNLOCK(); 643 644 return(error); 645 } 646 647 /* 648 * MPSAFE 649 */ 650 int 651 vop_old_link(struct vop_ops *ops, struct vnode *tdvp, 652 struct vnode *vp, struct componentname *cnp) 653 { 654 struct vop_old_link_args ap; 655 VFS_MPLOCK_DECLARE; 656 int error; 657 658 ap.a_head.a_desc = &vop_old_link_desc; 659 ap.a_head.a_ops = ops; 660 ap.a_tdvp = tdvp; 661 ap.a_vp = vp; 662 ap.a_cnp = cnp; 663 664 VFS_MPLOCK(tdvp->v_mount); 665 DO_OPS(ops, error, &ap, vop_old_link); 666 VFS_MPUNLOCK(); 667 668 return(error); 669 } 670 671 /* 672 * MPSAFE 673 */ 674 int 675 vop_old_rename(struct vop_ops *ops, 676 struct vnode *fdvp, struct vnode *fvp, struct componentname *fcnp, 677 struct vnode *tdvp, struct vnode *tvp, struct componentname *tcnp) 678 { 679 struct vop_old_rename_args ap; 680 VFS_MPLOCK_DECLARE; 681 int error; 682 683 ap.a_head.a_desc = &vop_old_rename_desc; 684 ap.a_head.a_ops = ops; 685 ap.a_fdvp = fdvp; 686 ap.a_fvp = fvp; 687 ap.a_fcnp = fcnp; 688 ap.a_tdvp = tdvp; 689 ap.a_tvp = tvp; 690 ap.a_tcnp = tcnp; 691 692 VFS_MPLOCK(tdvp->v_mount); 693 DO_OPS(ops, error, &ap, vop_old_rename); 694 VFS_MPUNLOCK(); 695 696 return(error); 697 } 698 699 /* 700 * MPSAFE 701 */ 702 int 703 vop_old_mkdir(struct vop_ops *ops, struct vnode *dvp, 704 struct vnode **vpp, struct componentname *cnp, struct vattr *vap) 705 { 706 struct vop_old_mkdir_args ap; 707 VFS_MPLOCK_DECLARE; 708 int error; 709 710 ap.a_head.a_desc = &vop_old_mkdir_desc; 711 ap.a_head.a_ops = ops; 712 ap.a_dvp = dvp; 713 ap.a_vpp = vpp; 714 ap.a_cnp = cnp; 715 ap.a_vap = vap; 716 717 VFS_MPLOCK(dvp->v_mount); 718 DO_OPS(ops, error, &ap, vop_old_mkdir); 719 VFS_MPUNLOCK(); 720 721 return(error); 722 } 723 724 /* 725 * MPSAFE 726 */ 727 int 728 vop_old_rmdir(struct vop_ops *ops, struct vnode *dvp, 729 struct vnode *vp, struct componentname *cnp) 730 { 731 struct vop_old_rmdir_args ap; 732 VFS_MPLOCK_DECLARE; 733 int error; 734 735 ap.a_head.a_desc = &vop_old_rmdir_desc; 736 ap.a_head.a_ops = ops; 737 ap.a_dvp = dvp; 738 ap.a_vp = vp; 739 ap.a_cnp = cnp; 740 741 VFS_MPLOCK(dvp->v_mount); 742 DO_OPS(ops, error, &ap, vop_old_rmdir); 743 VFS_MPUNLOCK(); 744 745 return(error); 746 } 747 748 /* 749 * MPSAFE 750 */ 751 int 752 vop_old_symlink(struct vop_ops *ops, struct vnode *dvp, 753 struct vnode **vpp, struct componentname *cnp, 754 struct vattr *vap, char *target) 755 { 756 struct vop_old_symlink_args ap; 757 VFS_MPLOCK_DECLARE; 758 int error; 759 760 ap.a_head.a_desc = &vop_old_symlink_desc; 761 ap.a_head.a_ops = ops; 762 ap.a_dvp = dvp; 763 ap.a_vpp = vpp; 764 ap.a_cnp = cnp; 765 ap.a_vap = vap; 766 ap.a_target = target; 767 768 VFS_MPLOCK(dvp->v_mount); 769 DO_OPS(ops, error, &ap, vop_old_symlink); 770 VFS_MPUNLOCK(); 771 772 return(error); 773 } 774 775 /* 776 * MPSAFE 777 */ 778 int 779 vop_readdir(struct vop_ops *ops, struct vnode *vp, struct uio *uio, 780 struct ucred *cred, int *eofflag, int *ncookies, off_t **cookies, 781 struct file *fp) 782 { 783 struct vop_readdir_args ap; 784 VFS_MPLOCK_DECLARE; 785 int error; 786 787 ap.a_head.a_desc = &vop_readdir_desc; 788 ap.a_head.a_ops = ops; 789 ap.a_vp = vp; 790 ap.a_uio = uio; 791 ap.a_cred = cred; 792 ap.a_eofflag = eofflag; 793 ap.a_ncookies = ncookies; 794 ap.a_cookies = cookies; 795 ap.a_fp = fp; 796 797 VFS_MPLOCK(vp->v_mount); 798 DO_OPS(ops, error, &ap, vop_readdir); 799 VFS_MPUNLOCK(); 800 801 return(error); 802 } 803 804 /* 805 * MPSAFE 806 */ 807 int 808 vop_readlink(struct vop_ops *ops, struct vnode *vp, struct uio *uio, 809 struct ucred *cred) 810 { 811 struct vop_readlink_args ap; 812 VFS_MPLOCK_DECLARE; 813 int error; 814 815 ap.a_head.a_desc = &vop_readlink_desc; 816 ap.a_head.a_ops = ops; 817 ap.a_vp = vp; 818 ap.a_uio = uio; 819 ap.a_cred = cred; 820 821 VFS_MPLOCK(vp->v_mount); 822 DO_OPS(ops, error, &ap, vop_readlink); 823 VFS_MPUNLOCK(); 824 825 return(error); 826 } 827 828 /* 829 * MPSAFE 830 */ 831 int 832 vop_inactive(struct vop_ops *ops, struct vnode *vp) 833 { 834 struct vop_inactive_args ap; 835 struct mount *mp; 836 VFS_MPLOCK_DECLARE; 837 int error; 838 839 ap.a_head.a_desc = &vop_inactive_desc; 840 ap.a_head.a_ops = ops; 841 ap.a_vp = vp; 842 843 /* 844 * WARNING! Deactivation of the vnode can cause it to be recycled, 845 * clearing vp->v_mount. 846 */ 847 mp = vp->v_mount; 848 VFS_MPLOCK_FLAG(mp, MNTK_IN_MPSAFE); 849 DO_OPS(ops, error, &ap, vop_inactive); 850 VFS_MPUNLOCK(); 851 852 return(error); 853 } 854 855 /* 856 * MPSAFE 857 */ 858 int 859 vop_reclaim(struct vop_ops *ops, struct vnode *vp) 860 { 861 struct vop_reclaim_args ap; 862 struct mount *mp; 863 VFS_MPLOCK_DECLARE; 864 int error; 865 866 ap.a_head.a_desc = &vop_reclaim_desc; 867 ap.a_head.a_ops = ops; 868 ap.a_vp = vp; 869 870 /* 871 * WARNING! Reclamation of the vnode will clear vp->v_mount. 872 */ 873 mp = vp->v_mount; 874 VFS_MPLOCK(mp); 875 DO_OPS(ops, error, &ap, vop_reclaim); 876 VFS_MPUNLOCK(); 877 878 return(error); 879 } 880 881 /* 882 * MPSAFE 883 */ 884 int 885 vop_bmap(struct vop_ops *ops, struct vnode *vp, off_t loffset, 886 off_t *doffsetp, int *runp, int *runb, buf_cmd_t cmd) 887 { 888 struct vop_bmap_args ap; 889 VFS_MPLOCK_DECLARE; 890 int error; 891 892 ap.a_head.a_desc = &vop_bmap_desc; 893 ap.a_head.a_ops = ops; 894 ap.a_vp = vp; 895 ap.a_loffset = loffset; 896 ap.a_doffsetp = doffsetp; 897 ap.a_runp = runp; 898 ap.a_runb = runb; 899 ap.a_cmd = cmd; 900 901 VFS_MPLOCK(vp->v_mount); 902 DO_OPS(ops, error, &ap, vop_bmap); 903 VFS_MPUNLOCK(); 904 905 return(error); 906 } 907 908 /* 909 * WARNING! Vnode can go-away after the ops call (e.g. async flush 910 * from buffer kthread). 911 */ 912 int 913 vop_strategy(struct vop_ops *ops, struct vnode *vp, struct bio *bio) 914 { 915 struct vop_strategy_args ap; 916 VFS_MPLOCK_DECLARE; 917 int error; 918 919 ap.a_head.a_desc = &vop_strategy_desc; 920 ap.a_head.a_ops = ops; 921 ap.a_vp = vp; 922 ap.a_bio = bio; 923 924 if (vp->v_mount) { 925 VFS_MPLOCK_FLAG(vp->v_mount, MNTK_SG_MPSAFE); 926 DO_OPS(ops, error, &ap, vop_strategy); 927 VFS_MPUNLOCK(); 928 } else { 929 /* ugly hack for swap */ 930 get_mplock(); 931 DO_OPS(ops, error, &ap, vop_strategy); 932 rel_mplock(); 933 } 934 return(error); 935 } 936 937 /* 938 * MPSAFE 939 */ 940 int 941 vop_print(struct vop_ops *ops, struct vnode *vp) 942 { 943 struct vop_print_args ap; 944 VFS_MPLOCK_DECLARE; 945 int error; 946 947 ap.a_head.a_desc = &vop_print_desc; 948 ap.a_head.a_ops = ops; 949 ap.a_vp = vp; 950 951 VFS_MPLOCK(vp->v_mount); 952 DO_OPS(ops, error, &ap, vop_print); 953 VFS_MPUNLOCK(); 954 955 return(error); 956 } 957 958 /* 959 * MPSAFE 960 */ 961 int 962 vop_pathconf(struct vop_ops *ops, struct vnode *vp, int name, 963 register_t *retval) 964 { 965 struct vop_pathconf_args ap; 966 VFS_MPLOCK_DECLARE; 967 int error; 968 969 ap.a_head.a_desc = &vop_pathconf_desc; 970 ap.a_head.a_ops = ops; 971 ap.a_vp = vp; 972 ap.a_name = name; 973 ap.a_retval = retval; 974 975 VFS_MPLOCK(vp->v_mount); 976 DO_OPS(ops, error, &ap, vop_pathconf); 977 VFS_MPUNLOCK(); 978 979 return(error); 980 } 981 982 /* 983 * MPSAFE 984 */ 985 int 986 vop_advlock(struct vop_ops *ops, struct vnode *vp, caddr_t id, int op, 987 struct flock *fl, int flags) 988 { 989 struct vop_advlock_args ap; 990 VFS_MPLOCK_DECLARE; 991 int error; 992 993 ap.a_head.a_desc = &vop_advlock_desc; 994 ap.a_head.a_ops = ops; 995 ap.a_vp = vp; 996 ap.a_id = id; 997 ap.a_op = op; 998 ap.a_fl = fl; 999 ap.a_flags = flags; 1000 1001 VFS_MPLOCK(vp->v_mount); 1002 DO_OPS(ops, error, &ap, vop_advlock); 1003 VFS_MPUNLOCK(); 1004 1005 return(error); 1006 } 1007 1008 /* 1009 * MPSAFE 1010 */ 1011 int 1012 vop_balloc(struct vop_ops *ops, struct vnode *vp, off_t startoffset, 1013 int size, struct ucred *cred, int flags, 1014 struct buf **bpp) 1015 { 1016 struct vop_balloc_args ap; 1017 VFS_MPLOCK_DECLARE; 1018 int error; 1019 1020 ap.a_head.a_desc = &vop_balloc_desc; 1021 ap.a_head.a_ops = ops; 1022 ap.a_vp = vp; 1023 ap.a_startoffset = startoffset; 1024 ap.a_size = size; 1025 ap.a_cred = cred; 1026 ap.a_flags = flags; 1027 ap.a_bpp = bpp; 1028 1029 VFS_MPLOCK(vp->v_mount); 1030 DO_OPS(ops, error, &ap, vop_balloc); 1031 VFS_MPUNLOCK(); 1032 1033 return(error); 1034 } 1035 1036 /* 1037 * MPSAFE 1038 */ 1039 int 1040 vop_reallocblks(struct vop_ops *ops, struct vnode *vp, 1041 struct cluster_save *buflist) 1042 { 1043 struct vop_reallocblks_args ap; 1044 VFS_MPLOCK_DECLARE; 1045 int error; 1046 1047 ap.a_head.a_desc = &vop_reallocblks_desc; 1048 ap.a_head.a_ops = ops; 1049 ap.a_vp = vp; 1050 ap.a_buflist = buflist; 1051 1052 VFS_MPLOCK(vp->v_mount); 1053 DO_OPS(ops, error, &ap, vop_reallocblks); 1054 VFS_MPUNLOCK(); 1055 1056 return(error); 1057 } 1058 1059 /* 1060 * MPSAFE 1061 */ 1062 int 1063 vop_getpages(struct vop_ops *ops, struct vnode *vp, vm_page_t *m, int count, 1064 int reqpage, vm_ooffset_t offset, int seqaccess) 1065 { 1066 struct vop_getpages_args ap; 1067 VFS_MPLOCK_DECLARE; 1068 int error; 1069 1070 ap.a_head.a_desc = &vop_getpages_desc; 1071 ap.a_head.a_ops = ops; 1072 ap.a_vp = vp; 1073 ap.a_m = m; 1074 ap.a_count = count; 1075 ap.a_reqpage = reqpage; 1076 ap.a_offset = offset; 1077 ap.a_seqaccess = seqaccess; 1078 1079 VFS_MPLOCK(vp->v_mount); 1080 DO_OPS(ops, error, &ap, vop_getpages); 1081 VFS_MPUNLOCK(); 1082 1083 return(error); 1084 } 1085 1086 /* 1087 * MPSAFE 1088 */ 1089 int 1090 vop_putpages(struct vop_ops *ops, struct vnode *vp, vm_page_t *m, int count, 1091 int flags, int *rtvals, vm_ooffset_t offset) 1092 { 1093 struct vop_putpages_args ap; 1094 VFS_MPLOCK_DECLARE; 1095 int error; 1096 1097 ap.a_head.a_desc = &vop_putpages_desc; 1098 ap.a_head.a_ops = ops; 1099 ap.a_vp = vp; 1100 ap.a_m = m; 1101 ap.a_count = count; 1102 ap.a_flags = flags; 1103 ap.a_rtvals = rtvals; 1104 ap.a_offset = offset; 1105 1106 VFS_MPLOCK(vp->v_mount); 1107 DO_OPS(ops, error, &ap, vop_putpages); 1108 VFS_MPUNLOCK(); 1109 1110 return(error); 1111 } 1112 1113 /* 1114 * MPSAFE 1115 */ 1116 int 1117 vop_freeblks(struct vop_ops *ops, struct vnode *vp, off_t offset, int length) 1118 { 1119 struct vop_freeblks_args ap; 1120 VFS_MPLOCK_DECLARE; 1121 int error; 1122 1123 ap.a_head.a_desc = &vop_freeblks_desc; 1124 ap.a_head.a_ops = ops; 1125 ap.a_vp = vp; 1126 ap.a_offset = offset; 1127 ap.a_length = length; 1128 1129 VFS_MPLOCK(vp->v_mount); 1130 DO_OPS(ops, error, &ap, vop_freeblks); 1131 VFS_MPUNLOCK(); 1132 1133 return(error); 1134 } 1135 1136 /* 1137 * MPSAFE 1138 */ 1139 int 1140 vop_getacl(struct vop_ops *ops, struct vnode *vp, acl_type_t type, 1141 struct acl *aclp, struct ucred *cred) 1142 { 1143 struct vop_getacl_args ap; 1144 VFS_MPLOCK_DECLARE; 1145 int error; 1146 1147 ap.a_head.a_desc = &vop_getacl_desc; 1148 ap.a_head.a_ops = ops; 1149 ap.a_vp = vp; 1150 ap.a_type = type; 1151 ap.a_aclp = aclp; 1152 ap.a_cred = cred; 1153 1154 VFS_MPLOCK(vp->v_mount); 1155 DO_OPS(ops, error, &ap, vop_getacl); 1156 VFS_MPUNLOCK(); 1157 1158 return(error); 1159 } 1160 1161 /* 1162 * MPSAFE 1163 */ 1164 int 1165 vop_setacl(struct vop_ops *ops, struct vnode *vp, acl_type_t type, 1166 struct acl *aclp, struct ucred *cred) 1167 { 1168 struct vop_setacl_args ap; 1169 VFS_MPLOCK_DECLARE; 1170 int error; 1171 1172 ap.a_head.a_desc = &vop_setacl_desc; 1173 ap.a_head.a_ops = ops; 1174 ap.a_vp = vp; 1175 ap.a_type = type; 1176 ap.a_aclp = aclp; 1177 ap.a_cred = cred; 1178 1179 VFS_MPLOCK(vp->v_mount); 1180 DO_OPS(ops, error, &ap, vop_setacl); 1181 VFS_MPUNLOCK(); 1182 1183 return(error); 1184 } 1185 1186 /* 1187 * MPSAFE 1188 */ 1189 int 1190 vop_aclcheck(struct vop_ops *ops, struct vnode *vp, acl_type_t type, 1191 struct acl *aclp, struct ucred *cred) 1192 { 1193 struct vop_aclcheck_args ap; 1194 VFS_MPLOCK_DECLARE; 1195 int error; 1196 1197 ap.a_head.a_desc = &vop_aclcheck_desc; 1198 ap.a_head.a_ops = ops; 1199 ap.a_vp = vp; 1200 ap.a_type = type; 1201 ap.a_aclp = aclp; 1202 ap.a_cred = cred; 1203 1204 VFS_MPLOCK(vp->v_mount); 1205 DO_OPS(ops, error, &ap, vop_aclcheck); 1206 VFS_MPUNLOCK(); 1207 1208 return(error); 1209 } 1210 1211 /* 1212 * MPSAFE 1213 */ 1214 int 1215 vop_getextattr(struct vop_ops *ops, struct vnode *vp, int attrnamespace, 1216 char *attrname, struct uio *uio, struct ucred *cred) 1217 { 1218 struct vop_getextattr_args ap; 1219 VFS_MPLOCK_DECLARE; 1220 int error; 1221 1222 ap.a_head.a_desc = &vop_getextattr_desc; 1223 ap.a_head.a_ops = ops; 1224 ap.a_vp = vp; 1225 ap.a_attrnamespace = attrnamespace; 1226 ap.a_attrname = attrname; 1227 ap.a_uio = uio; 1228 ap.a_cred = cred; 1229 1230 VFS_MPLOCK(vp->v_mount); 1231 DO_OPS(ops, error, &ap, vop_getextattr); 1232 VFS_MPUNLOCK(); 1233 1234 return(error); 1235 } 1236 1237 /* 1238 * MPSAFE 1239 */ 1240 int 1241 vop_setextattr(struct vop_ops *ops, struct vnode *vp, int attrnamespace, 1242 char *attrname, struct uio *uio, struct ucred *cred) 1243 { 1244 struct vop_setextattr_args ap; 1245 VFS_MPLOCK_DECLARE; 1246 int error; 1247 1248 ap.a_head.a_desc = &vop_setextattr_desc; 1249 ap.a_head.a_ops = ops; 1250 ap.a_vp = vp; 1251 ap.a_attrnamespace = attrnamespace; 1252 ap.a_attrname = attrname; 1253 ap.a_uio = uio; 1254 ap.a_cred = cred; 1255 1256 VFS_MPLOCK(vp->v_mount); 1257 DO_OPS(ops, error, &ap, vop_setextattr); 1258 VFS_MPUNLOCK(); 1259 1260 return(error); 1261 } 1262 1263 /* 1264 * MPSAFE 1265 */ 1266 int 1267 vop_mountctl(struct vop_ops *ops, struct vnode *vp, int op, struct file *fp, 1268 const void *ctl, int ctllen, void *buf, int buflen, int *res) 1269 { 1270 struct vop_mountctl_args ap; 1271 VFS_MPLOCK_DECLARE; 1272 int error; 1273 1274 ap.a_head.a_desc = &vop_mountctl_desc; 1275 ap.a_head.a_ops = ops; 1276 ap.a_op = op; 1277 ap.a_ctl = ctl; 1278 ap.a_fp = fp; 1279 ap.a_ctllen = ctllen; 1280 ap.a_buf = buf; 1281 ap.a_buflen = buflen; 1282 ap.a_res = res; 1283 1284 VFS_MPLOCK(vp->v_mount); 1285 DO_OPS(ops, error, &ap, vop_mountctl); 1286 VFS_MPUNLOCK(); 1287 1288 return(error); 1289 } 1290 1291 /* 1292 * MPSAFE 1293 */ 1294 int 1295 vop_markatime(struct vop_ops *ops, struct vnode *vp, struct ucred *cred) 1296 { 1297 struct vop_markatime_args ap; 1298 VFS_MPLOCK_DECLARE; 1299 int error; 1300 1301 ap.a_head.a_desc = &vop_markatime_desc; 1302 ap.a_head.a_ops = ops; 1303 ap.a_vp = vp; 1304 ap.a_cred = cred; 1305 1306 VFS_MPLOCK(vp->v_mount); 1307 DO_OPS(ops, error, &ap, vop_markatime); 1308 VFS_MPUNLOCK(); 1309 1310 return(error); 1311 } 1312 1313 /* 1314 * MPSAFE 1315 */ 1316 int 1317 vop_allocate(struct vop_ops *ops, struct vnode *vp, off_t offset, off_t len) 1318 { 1319 struct vop_allocate_args ap; 1320 VFS_MPLOCK_DECLARE; 1321 int error; 1322 1323 ap.a_head.a_desc = &vop_allocate_desc; 1324 ap.a_head.a_ops = ops; 1325 ap.a_vp = vp; 1326 ap.a_offset = 0; 1327 ap.a_len = len; 1328 1329 VFS_MPLOCK(vp->v_mount); 1330 DO_OPS(ops, error, &ap, vop_allocate); 1331 VFS_MPUNLOCK(); 1332 1333 return(error); 1334 } 1335 1336 /* 1337 * NEW API FUNCTIONS 1338 * 1339 * nresolve takes a locked ncp, a referenced but unlocked dvp, and a cred, 1340 * and resolves the ncp into a positive or negative hit. 1341 * 1342 * The namecache is automatically adjusted by this function. The ncp 1343 * is left locked on return. 1344 * 1345 * MPSAFE 1346 */ 1347 int 1348 vop_nresolve(struct vop_ops *ops, struct nchandle *nch, 1349 struct vnode *dvp, struct ucred *cred) 1350 { 1351 struct vop_nresolve_args ap; 1352 VFS_MPLOCK_DECLARE; 1353 int error; 1354 1355 ap.a_head.a_desc = &vop_nresolve_desc; 1356 ap.a_head.a_ops = ops; 1357 ap.a_nch = nch; 1358 ap.a_dvp = dvp; 1359 ap.a_cred = cred; 1360 1361 VFS_MPLOCK(dvp->v_mount); 1362 DO_OPS(ops, error, &ap, vop_nresolve); 1363 VFS_MPUNLOCK(); 1364 1365 return(error); 1366 } 1367 1368 /* 1369 * nlookupdotdot takes an unlocked directory, referenced dvp, and looks 1370 * up "..", returning a locked parent directory in *vpp. If an error 1371 * occurs *vpp will be NULL. 1372 * 1373 * MPSAFE 1374 */ 1375 int 1376 vop_nlookupdotdot(struct vop_ops *ops, struct vnode *dvp, 1377 struct vnode **vpp, struct ucred *cred, char **fakename) 1378 { 1379 struct vop_nlookupdotdot_args ap; 1380 VFS_MPLOCK_DECLARE; 1381 int error; 1382 1383 ap.a_head.a_desc = &vop_nlookupdotdot_desc; 1384 ap.a_head.a_ops = ops; 1385 ap.a_dvp = dvp; 1386 ap.a_vpp = vpp; 1387 ap.a_cred = cred; 1388 ap.a_fakename = fakename; 1389 1390 VFS_MPLOCK(dvp->v_mount); 1391 DO_OPS(ops, error, &ap, vop_nlookupdotdot); 1392 VFS_MPUNLOCK(); 1393 1394 return(error); 1395 } 1396 1397 /* 1398 * ncreate takes a locked, resolved ncp that typically represents a negative 1399 * cache hit and creates the file or node specified by the ncp, cred, and 1400 * vattr. If no error occurs a locked vnode is returned in *vpp. 1401 * 1402 * The dvp passed in is referenced but unlocked. 1403 * 1404 * The namecache is automatically adjusted by this function. The ncp 1405 * is left locked on return. 1406 * 1407 * MPSAFE 1408 */ 1409 int 1410 vop_ncreate(struct vop_ops *ops, struct nchandle *nch, struct vnode *dvp, 1411 struct vnode **vpp, struct ucred *cred, struct vattr *vap) 1412 { 1413 struct vop_ncreate_args ap; 1414 VFS_MPLOCK_DECLARE; 1415 int error; 1416 1417 ap.a_head.a_desc = &vop_ncreate_desc; 1418 ap.a_head.a_ops = ops; 1419 ap.a_nch = nch; 1420 ap.a_dvp = dvp; 1421 ap.a_vpp = vpp; 1422 ap.a_cred = cred; 1423 ap.a_vap = vap; 1424 1425 VFS_MPLOCK(dvp->v_mount); 1426 DO_OPS(ops, error, &ap, vop_ncreate); 1427 VFS_MPUNLOCK(); 1428 1429 return(error); 1430 } 1431 1432 /* 1433 * nmkdir takes a locked, resolved ncp that typically represents a negative 1434 * cache hit and creates the directory specified by the ncp, cred, and 1435 * vattr. If no error occurs a locked vnode is returned in *vpp. 1436 * 1437 * The dvp passed in is referenced but unlocked. 1438 * 1439 * The namecache is automatically adjusted by this function. The ncp 1440 * is left locked on return. 1441 * 1442 * MPSAFE 1443 */ 1444 int 1445 vop_nmkdir(struct vop_ops *ops, struct nchandle *nch, struct vnode *dvp, 1446 struct vnode **vpp, struct ucred *cred, struct vattr *vap) 1447 { 1448 struct vop_nmkdir_args ap; 1449 VFS_MPLOCK_DECLARE; 1450 int error; 1451 1452 ap.a_head.a_desc = &vop_nmkdir_desc; 1453 ap.a_head.a_ops = ops; 1454 ap.a_nch = nch; 1455 ap.a_dvp = dvp; 1456 ap.a_vpp = vpp; 1457 ap.a_cred = cred; 1458 ap.a_vap = vap; 1459 1460 VFS_MPLOCK(dvp->v_mount); 1461 DO_OPS(ops, error, &ap, vop_nmkdir); 1462 VFS_MPUNLOCK(); 1463 1464 return(error); 1465 } 1466 1467 /* 1468 * nmknod takes a locked, resolved ncp that typically represents a negative 1469 * cache hit and creates the node specified by the ncp, cred, and 1470 * vattr. If no error occurs a locked vnode is returned in *vpp. 1471 * 1472 * The dvp passed in is referenced but unlocked. 1473 * 1474 * The namecache is automatically adjusted by this function. The ncp 1475 * is left locked on return. 1476 * 1477 * MPSAFE 1478 */ 1479 int 1480 vop_nmknod(struct vop_ops *ops, struct nchandle *nch, struct vnode *dvp, 1481 struct vnode **vpp, struct ucred *cred, struct vattr *vap) 1482 { 1483 struct vop_nmknod_args ap; 1484 VFS_MPLOCK_DECLARE; 1485 int error; 1486 1487 ap.a_head.a_desc = &vop_nmknod_desc; 1488 ap.a_head.a_ops = ops; 1489 ap.a_nch = nch; 1490 ap.a_dvp = dvp; 1491 ap.a_vpp = vpp; 1492 ap.a_cred = cred; 1493 ap.a_vap = vap; 1494 1495 VFS_MPLOCK(dvp->v_mount); 1496 DO_OPS(ops, error, &ap, vop_nmknod); 1497 VFS_MPUNLOCK(); 1498 1499 return(error); 1500 } 1501 1502 /* 1503 * nlink takes a locked, resolved ncp that typically represents a negative 1504 * cache hit and creates the node specified by the ncp, cred, and 1505 * existing vnode. The passed vp must be locked and will remain locked 1506 * on return, as does the ncp, whether an error occurs or not. 1507 * 1508 * The dvp passed in is referenced but unlocked. 1509 * 1510 * The namecache is automatically adjusted by this function. The ncp 1511 * is left locked on return. 1512 * 1513 * MPSAFE 1514 */ 1515 int 1516 vop_nlink(struct vop_ops *ops, struct nchandle *nch, struct vnode *dvp, 1517 struct vnode *vp, struct ucred *cred) 1518 { 1519 struct vop_nlink_args ap; 1520 VFS_MPLOCK_DECLARE; 1521 int error; 1522 1523 ap.a_head.a_desc = &vop_nlink_desc; 1524 ap.a_head.a_ops = ops; 1525 ap.a_nch = nch; 1526 ap.a_dvp = dvp; 1527 ap.a_vp = vp; 1528 ap.a_cred = cred; 1529 1530 VFS_MPLOCK(dvp->v_mount); 1531 DO_OPS(ops, error, &ap, vop_nlink); 1532 VFS_MPUNLOCK(); 1533 1534 return(error); 1535 } 1536 1537 /* 1538 * nsymlink takes a locked, resolved ncp that typically represents a negative 1539 * cache hit and creates a symbolic link based on cred, vap, and target (the 1540 * contents of the link). If no error occurs a locked vnode is returned in 1541 * *vpp. 1542 * 1543 * The dvp passed in is referenced but unlocked. 1544 * 1545 * The namecache is automatically adjusted by this function. The ncp 1546 * is left locked on return. 1547 * 1548 * MPSAFE 1549 */ 1550 int 1551 vop_nsymlink(struct vop_ops *ops, struct nchandle *nch, struct vnode *dvp, 1552 struct vnode **vpp, struct ucred *cred, 1553 struct vattr *vap, char *target) 1554 { 1555 struct vop_nsymlink_args ap; 1556 VFS_MPLOCK_DECLARE; 1557 int error; 1558 1559 ap.a_head.a_desc = &vop_nsymlink_desc; 1560 ap.a_head.a_ops = ops; 1561 ap.a_nch = nch; 1562 ap.a_dvp = dvp; 1563 ap.a_vpp = vpp; 1564 ap.a_cred = cred; 1565 ap.a_vap = vap; 1566 ap.a_target = target; 1567 1568 VFS_MPLOCK(dvp->v_mount); 1569 DO_OPS(ops, error, &ap, vop_nsymlink); 1570 VFS_MPUNLOCK(); 1571 1572 return(error); 1573 } 1574 1575 /* 1576 * nwhiteout takes a locked, resolved ncp that can represent a positive or 1577 * negative hit and executes the whiteout function specified in flags. 1578 * 1579 * The dvp passed in is referenced but unlocked. 1580 * 1581 * The namecache is automatically adjusted by this function. The ncp 1582 * is left locked on return. 1583 * 1584 * MPSAFE 1585 */ 1586 int 1587 vop_nwhiteout(struct vop_ops *ops, struct nchandle *nch, struct vnode *dvp, 1588 struct ucred *cred, int flags) 1589 { 1590 struct vop_nwhiteout_args ap; 1591 VFS_MPLOCK_DECLARE; 1592 int error; 1593 1594 ap.a_head.a_desc = &vop_nwhiteout_desc; 1595 ap.a_head.a_ops = ops; 1596 ap.a_nch = nch; 1597 ap.a_dvp = dvp; 1598 ap.a_cred = cred; 1599 ap.a_flags = flags; 1600 1601 VFS_MPLOCK(dvp->v_mount); 1602 DO_OPS(ops, error, &ap, vop_nwhiteout); 1603 VFS_MPUNLOCK(); 1604 1605 return(error); 1606 } 1607 1608 /* 1609 * nremove takes a locked, resolved ncp that generally represents a 1610 * positive hit and removes the file. 1611 * 1612 * The dvp passed in is referenced but unlocked. 1613 * 1614 * The namecache is automatically adjusted by this function. The ncp 1615 * is left locked on return. 1616 * 1617 * MPSAFE 1618 */ 1619 int 1620 vop_nremove(struct vop_ops *ops, struct nchandle *nch, struct vnode *dvp, 1621 struct ucred *cred) 1622 { 1623 struct vop_nremove_args ap; 1624 VFS_MPLOCK_DECLARE; 1625 int error; 1626 struct vattr va; 1627 1628 ap.a_head.a_desc = &vop_nremove_desc; 1629 ap.a_head.a_ops = ops; 1630 ap.a_nch = nch; 1631 ap.a_dvp = dvp; 1632 ap.a_cred = cred; 1633 1634 if ((error = VOP_GETATTR(nch->ncp->nc_vp, &va)) != 0) 1635 return (error); 1636 1637 VFS_MPLOCK(dvp->v_mount); 1638 DO_OPS(ops, error, &ap, vop_nremove); 1639 /* Only update space counters if this is the last hard link */ 1640 if ((error == 0) && (va.va_nlink == 1)) { 1641 VFS_ACCOUNT(nch->mount, va.va_uid, va.va_gid, -va.va_size); 1642 } 1643 VFS_MPUNLOCK(); 1644 1645 return(error); 1646 } 1647 1648 /* 1649 * nrmdir takes a locked, resolved ncp that generally represents a 1650 * directory and removes the directory. 1651 * 1652 * The dvp passed in is referenced but unlocked. 1653 * 1654 * The namecache is automatically adjusted by this function. The ncp 1655 * is left locked on return. 1656 * 1657 * MPSAFE 1658 */ 1659 int 1660 vop_nrmdir(struct vop_ops *ops, struct nchandle *nch, struct vnode *dvp, 1661 struct ucred *cred) 1662 { 1663 struct vop_nrmdir_args ap; 1664 VFS_MPLOCK_DECLARE; 1665 int error; 1666 1667 ap.a_head.a_desc = &vop_nrmdir_desc; 1668 ap.a_head.a_ops = ops; 1669 ap.a_nch = nch; 1670 ap.a_dvp = dvp; 1671 ap.a_cred = cred; 1672 1673 VFS_MPLOCK(dvp->v_mount); 1674 DO_OPS(ops, error, &ap, vop_nrmdir); 1675 VFS_MPUNLOCK(); 1676 1677 return(error); 1678 } 1679 1680 /* 1681 * nrename takes TWO locked, resolved ncp's and the cred of the caller 1682 * and renames the source ncp to the target ncp. The target ncp may 1683 * represent a positive or negative hit. 1684 * 1685 * The fdvp and tdvp passed in are referenced but unlocked. 1686 * 1687 * The namecache is automatically adjusted by this function. The ncp 1688 * is left locked on return. The source ncp is typically changed to 1689 * a negative cache hit and the target ncp typically takes on the 1690 * source ncp's underlying file. 1691 * 1692 * MPSAFE 1693 */ 1694 int 1695 vop_nrename(struct vop_ops *ops, 1696 struct nchandle *fnch, struct nchandle *tnch, 1697 struct vnode *fdvp, struct vnode *tdvp, 1698 struct ucred *cred) 1699 { 1700 struct vop_nrename_args ap; 1701 VFS_MPLOCK_DECLARE; 1702 int error; 1703 1704 ap.a_head.a_desc = &vop_nrename_desc; 1705 ap.a_head.a_ops = ops; 1706 ap.a_fnch = fnch; 1707 ap.a_tnch = tnch; 1708 ap.a_fdvp = fdvp; 1709 ap.a_tdvp = tdvp; 1710 ap.a_cred = cred; 1711 1712 VFS_MPLOCK(fdvp->v_mount); 1713 DO_OPS(ops, error, &ap, vop_nrename); 1714 VFS_MPUNLOCK(); 1715 1716 return(error); 1717 } 1718 1719 /************************************************************************ 1720 * PRIMARY VNODE OPERATIONS FORWARDING CALLS * 1721 ************************************************************************ 1722 * 1723 * These procedures are called from VFSs such as nullfs 1724 * when they wish to forward an operation on one VFS to another. The 1725 * argument structure/message is modified and then directly passed to the 1726 * appropriate routine. This routines may also be called by initiators 1727 * who have an argument structure in hand rather then discreet arguments. 1728 * 1729 * MPSAFE - Caller expected to already hold the appropriate vfs lock. 1730 */ 1731 int 1732 vop_vnoperate_ap(struct vop_generic_args *ap) 1733 { 1734 struct vop_ops *ops; 1735 int error; 1736 1737 ops = ap->a_ops; 1738 error = VOCALL(ops, ap); 1739 1740 return (error); 1741 } 1742 1743 /* 1744 * This routine is called by the cache coherency layer to execute the actual 1745 * VFS operation. If a journaling layer is present we call though it, else 1746 * we call the native VOP functions. 1747 */ 1748 int 1749 vop_cache_operate_ap(struct vop_generic_args *ap) 1750 { 1751 struct vop_ops *ops; 1752 int error; 1753 1754 ops = ap->a_ops; 1755 if (ops->head.vv_mount->mnt_vn_journal_ops) 1756 error = VOCALL(ops->head.vv_mount->mnt_vn_journal_ops, ap); 1757 else 1758 error = VOCALL(ops->head.vv_mount->mnt_vn_norm_ops, ap); 1759 return (error); 1760 } 1761 1762 1763 /* 1764 * This routine is called by the journaling layer to execute the actual 1765 * VFS operation. 1766 */ 1767 int 1768 vop_journal_operate_ap(struct vop_generic_args *ap) 1769 { 1770 struct vop_ops *ops; 1771 int error; 1772 1773 ops = ap->a_ops; 1774 error = VOCALL(ops->head.vv_mount->mnt_vn_norm_ops, ap); 1775 1776 return (error); 1777 } 1778 1779 int 1780 vop_open_ap(struct vop_open_args *ap) 1781 { 1782 int error; 1783 1784 DO_OPS(ap->a_head.a_ops, error, ap, vop_open); 1785 return(error); 1786 } 1787 1788 int 1789 vop_close_ap(struct vop_close_args *ap) 1790 { 1791 int error; 1792 1793 DO_OPS(ap->a_head.a_ops, error, ap, vop_close); 1794 return(error); 1795 } 1796 1797 int 1798 vop_access_ap(struct vop_access_args *ap) 1799 { 1800 int error; 1801 1802 DO_OPS(ap->a_head.a_ops, error, ap, vop_access); 1803 return(error); 1804 } 1805 1806 int 1807 vop_getattr_ap(struct vop_getattr_args *ap) 1808 { 1809 int error; 1810 1811 DO_OPS(ap->a_head.a_ops, error, ap, vop_getattr); 1812 return(error); 1813 } 1814 1815 int 1816 vop_getattr_lite_ap(struct vop_getattr_lite_args *ap) 1817 { 1818 int error; 1819 1820 DO_OPS(ap->a_head.a_ops, error, ap, vop_getattr_lite); 1821 return(error); 1822 } 1823 1824 int 1825 vop_setattr_ap(struct vop_setattr_args *ap) 1826 { 1827 int error; 1828 1829 DO_OPS(ap->a_head.a_ops, error, ap, vop_setattr); 1830 return(error); 1831 } 1832 1833 int 1834 vop_read_ap(struct vop_read_args *ap) 1835 { 1836 int error; 1837 1838 DO_OPS(ap->a_head.a_ops, error, ap, vop_read); 1839 return(error); 1840 } 1841 1842 int 1843 vop_write_ap(struct vop_write_args *ap) 1844 { 1845 int error; 1846 1847 DO_OPS(ap->a_head.a_ops, error, ap, vop_write); 1848 return(error); 1849 } 1850 1851 int 1852 vop_ioctl_ap(struct vop_ioctl_args *ap) 1853 { 1854 int error; 1855 1856 DO_OPS(ap->a_head.a_ops, error, ap, vop_ioctl); 1857 return(error); 1858 } 1859 1860 int 1861 vop_poll_ap(struct vop_poll_args *ap) 1862 { 1863 int error; 1864 1865 DO_OPS(ap->a_head.a_ops, error, ap, vop_poll); 1866 return(error); 1867 } 1868 1869 int 1870 vop_kqfilter_ap(struct vop_kqfilter_args *ap) 1871 { 1872 int error; 1873 1874 DO_OPS(ap->a_head.a_ops, error, ap, vop_kqfilter); 1875 return(error); 1876 } 1877 1878 int 1879 vop_mmap_ap(struct vop_mmap_args *ap) 1880 { 1881 int error; 1882 1883 DO_OPS(ap->a_head.a_ops, error, ap, vop_mmap); 1884 return(error); 1885 } 1886 1887 int 1888 vop_fsync_ap(struct vop_fsync_args *ap) 1889 { 1890 int error; 1891 1892 DO_OPS(ap->a_head.a_ops, error, ap, vop_fsync); 1893 return(error); 1894 } 1895 1896 int 1897 vop_readdir_ap(struct vop_readdir_args *ap) 1898 { 1899 int error; 1900 1901 DO_OPS(ap->a_head.a_ops, error, ap, vop_readdir); 1902 return(error); 1903 } 1904 1905 int 1906 vop_readlink_ap(struct vop_readlink_args *ap) 1907 { 1908 int error; 1909 1910 DO_OPS(ap->a_head.a_ops, error, ap, vop_readlink); 1911 return(error); 1912 } 1913 1914 int 1915 vop_inactive_ap(struct vop_inactive_args *ap) 1916 { 1917 int error; 1918 1919 DO_OPS(ap->a_head.a_ops, error, ap, vop_inactive); 1920 return(error); 1921 } 1922 1923 int 1924 vop_reclaim_ap(struct vop_reclaim_args *ap) 1925 { 1926 int error; 1927 1928 DO_OPS(ap->a_head.a_ops, error, ap, vop_reclaim); 1929 return(error); 1930 } 1931 1932 int 1933 vop_bmap_ap(struct vop_bmap_args *ap) 1934 { 1935 int error; 1936 1937 DO_OPS(ap->a_head.a_ops, error, ap, vop_bmap); 1938 return(error); 1939 } 1940 1941 int 1942 vop_strategy_ap(struct vop_strategy_args *ap) 1943 { 1944 int error; 1945 1946 DO_OPS(ap->a_head.a_ops, error, ap, vop_strategy); 1947 return(error); 1948 } 1949 1950 int 1951 vop_print_ap(struct vop_print_args *ap) 1952 { 1953 int error; 1954 1955 DO_OPS(ap->a_head.a_ops, error, ap, vop_print); 1956 return(error); 1957 } 1958 1959 int 1960 vop_pathconf_ap(struct vop_pathconf_args *ap) 1961 { 1962 int error; 1963 1964 DO_OPS(ap->a_head.a_ops, error, ap, vop_pathconf); 1965 return(error); 1966 } 1967 1968 int 1969 vop_advlock_ap(struct vop_advlock_args *ap) 1970 { 1971 int error; 1972 1973 DO_OPS(ap->a_head.a_ops, error, ap, vop_advlock); 1974 return(error); 1975 } 1976 1977 int 1978 vop_balloc_ap(struct vop_balloc_args *ap) 1979 { 1980 int error; 1981 1982 DO_OPS(ap->a_head.a_ops, error, ap, vop_balloc); 1983 return(error); 1984 } 1985 1986 int 1987 vop_reallocblks_ap(struct vop_reallocblks_args *ap) 1988 { 1989 int error; 1990 1991 DO_OPS(ap->a_head.a_ops, error, ap, vop_reallocblks); 1992 return(error); 1993 } 1994 1995 int 1996 vop_getpages_ap(struct vop_getpages_args *ap) 1997 { 1998 int error; 1999 2000 DO_OPS(ap->a_head.a_ops, error, ap, vop_getpages); 2001 return(error); 2002 } 2003 2004 int 2005 vop_putpages_ap(struct vop_putpages_args *ap) 2006 { 2007 int error; 2008 2009 DO_OPS(ap->a_head.a_ops, error, ap, vop_putpages); 2010 return(error); 2011 } 2012 2013 int 2014 vop_freeblks_ap(struct vop_freeblks_args *ap) 2015 { 2016 int error; 2017 2018 DO_OPS(ap->a_head.a_ops, error, ap, vop_freeblks); 2019 return(error); 2020 } 2021 2022 int 2023 vop_getacl_ap(struct vop_getacl_args *ap) 2024 { 2025 int error; 2026 2027 DO_OPS(ap->a_head.a_ops, error, ap, vop_getacl); 2028 return(error); 2029 } 2030 2031 int 2032 vop_setacl_ap(struct vop_setacl_args *ap) 2033 { 2034 int error; 2035 2036 DO_OPS(ap->a_head.a_ops, error, ap, vop_setacl); 2037 return(error); 2038 } 2039 2040 int 2041 vop_aclcheck_ap(struct vop_aclcheck_args *ap) 2042 { 2043 int error; 2044 2045 DO_OPS(ap->a_head.a_ops, error, ap, vop_aclcheck); 2046 return(error); 2047 } 2048 2049 int 2050 vop_getextattr_ap(struct vop_getextattr_args *ap) 2051 { 2052 int error; 2053 2054 DO_OPS(ap->a_head.a_ops, error, ap, vop_getextattr); 2055 return(error); 2056 } 2057 2058 int 2059 vop_setextattr_ap(struct vop_setextattr_args *ap) 2060 { 2061 int error; 2062 2063 DO_OPS(ap->a_head.a_ops, error, ap, vop_setextattr); 2064 return(error); 2065 } 2066 2067 int 2068 vop_mountctl_ap(struct vop_mountctl_args *ap) 2069 { 2070 int error; 2071 2072 DO_OPS(ap->a_head.a_ops, error, ap, vop_mountctl); 2073 return(error); 2074 } 2075 2076 int 2077 vop_markatime_ap(struct vop_markatime_args *ap) 2078 { 2079 int error; 2080 2081 DO_OPS(ap->a_head.a_ops, error, ap, vop_markatime); 2082 return(error); 2083 } 2084 2085 int 2086 vop_allocate_ap(struct vop_allocate_args *ap) 2087 { 2088 int error; 2089 2090 DO_OPS(ap->a_head.a_ops, error, ap, vop_allocate); 2091 return(error); 2092 } 2093 2094 int 2095 vop_nresolve_ap(struct vop_nresolve_args *ap) 2096 { 2097 int error; 2098 2099 DO_OPS(ap->a_head.a_ops, error, ap, vop_nresolve); 2100 return(error); 2101 } 2102 2103 int 2104 vop_nlookupdotdot_ap(struct vop_nlookupdotdot_args *ap) 2105 { 2106 int error; 2107 2108 DO_OPS(ap->a_head.a_ops, error, ap, vop_nlookupdotdot); 2109 return(error); 2110 } 2111 2112 int 2113 vop_ncreate_ap(struct vop_ncreate_args *ap) 2114 { 2115 int error; 2116 2117 DO_OPS(ap->a_head.a_ops, error, ap, vop_ncreate); 2118 return(error); 2119 } 2120 2121 int 2122 vop_nmkdir_ap(struct vop_nmkdir_args *ap) 2123 { 2124 int error; 2125 2126 DO_OPS(ap->a_head.a_ops, error, ap, vop_nmkdir); 2127 return(error); 2128 } 2129 2130 int 2131 vop_nmknod_ap(struct vop_nmknod_args *ap) 2132 { 2133 int error; 2134 2135 DO_OPS(ap->a_head.a_ops, error, ap, vop_nmknod); 2136 return(error); 2137 } 2138 2139 int 2140 vop_nlink_ap(struct vop_nlink_args *ap) 2141 { 2142 int error; 2143 2144 DO_OPS(ap->a_head.a_ops, error, ap, vop_nlink); 2145 return(error); 2146 } 2147 2148 int 2149 vop_nsymlink_ap(struct vop_nsymlink_args *ap) 2150 { 2151 int error; 2152 2153 DO_OPS(ap->a_head.a_ops, error, ap, vop_nsymlink); 2154 return(error); 2155 } 2156 2157 int 2158 vop_nwhiteout_ap(struct vop_nwhiteout_args *ap) 2159 { 2160 int error; 2161 2162 DO_OPS(ap->a_head.a_ops, error, ap, vop_nwhiteout); 2163 return(error); 2164 } 2165 2166 int 2167 vop_nremove_ap(struct vop_nremove_args *ap) 2168 { 2169 int error; 2170 2171 DO_OPS(ap->a_head.a_ops, error, ap, vop_nremove); 2172 return(error); 2173 } 2174 2175 int 2176 vop_nrmdir_ap(struct vop_nrmdir_args *ap) 2177 { 2178 int error; 2179 2180 DO_OPS(ap->a_head.a_ops, error, ap, vop_nrmdir); 2181 return(error); 2182 } 2183 2184 int 2185 vop_nrename_ap(struct vop_nrename_args *ap) 2186 { 2187 int error; 2188 2189 DO_OPS(ap->a_head.a_ops, error, ap, vop_nrename); 2190 return(error); 2191 } 2192 2193