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