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