Dump entries can have the same timestamp, so accept those as well.
[dragonfly.git] / sys / kern / vfs_default.c
blobee24f5401f65d1f3d0ac7d8febee083bda109569
1 /*
2 * Copyright (c) 1989, 1993
3 * The Regents of the University of California. All rights reserved.
5 * This code is derived from software contributed
6 * to Berkeley by John Heidemann of the UCLA Ficus project.
8 * Source: * @(#)i405_init.c 2.10 92/04/27 UCLA Ficus project
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 * 1. Redistributions of source code must retain the above copyright
14 * notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 * notice, this list of conditions and the following disclaimer in the
17 * documentation and/or other materials provided with the distribution.
18 * 3. All advertising materials mentioning features or use of this software
19 * must display the following acknowledgement:
20 * This product includes software developed by the University of
21 * California, Berkeley and its contributors.
22 * 4. Neither the name of the University nor the names of its contributors
23 * may be used to endorse or promote products derived from this software
24 * without specific prior written permission.
26 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
27 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
28 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
29 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
30 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
31 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
32 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
33 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
34 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
35 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
36 * SUCH DAMAGE.
39 * $FreeBSD: src/sys/kern/vfs_default.c,v 1.28.2.7 2003/01/10 18:23:26 bde Exp $
40 * $DragonFly: src/sys/kern/vfs_default.c,v 1.52 2008/01/18 19:13:16 dillon Exp $
43 #include <sys/param.h>
44 #include <sys/systm.h>
45 #include <sys/buf.h>
46 #include <sys/conf.h>
47 #include <sys/fcntl.h>
48 #include <sys/file.h>
49 #include <sys/kernel.h>
50 #include <sys/lock.h>
51 #include <sys/malloc.h>
52 #include <sys/mount.h>
53 #include <sys/unistd.h>
54 #include <sys/vnode.h>
55 #include <sys/namei.h>
56 #include <sys/nlookup.h>
57 #include <sys/poll.h>
58 #include <sys/mountctl.h>
60 #include <machine/limits.h>
62 #include <vm/vm.h>
63 #include <vm/vm_object.h>
64 #include <vm/vm_page.h>
65 #include <vm/vm_pager.h>
66 #include <vm/vnode_pager.h>
68 static int vop_nolookup (struct vop_old_lookup_args *);
69 static int vop_nostrategy (struct vop_strategy_args *);
72 * This vnode table stores what we want to do if the filesystem doesn't
73 * implement a particular VOP.
75 * If there is no specific entry here, we will return EOPNOTSUPP.
77 struct vop_ops default_vnode_vops = {
78 .vop_default = vop_eopnotsupp,
79 .vop_advlock = (void *)vop_einval,
80 .vop_fsync = (void *)vop_null,
81 .vop_ioctl = (void *)vop_enotty,
82 .vop_mmap = (void *)vop_einval,
83 .vop_old_lookup = vop_nolookup,
84 .vop_open = vop_stdopen,
85 .vop_close = vop_stdclose,
86 .vop_pathconf = (void *)vop_einval,
87 .vop_poll = vop_nopoll,
88 .vop_readlink = (void *)vop_einval,
89 .vop_reallocblks = (void *)vop_eopnotsupp,
90 .vop_revoke = vop_stdrevoke,
91 .vop_strategy = vop_nostrategy,
92 .vop_getacl = (void *)vop_eopnotsupp,
93 .vop_setacl = (void *)vop_eopnotsupp,
94 .vop_aclcheck = (void *)vop_eopnotsupp,
95 .vop_getextattr = (void *)vop_eopnotsupp,
96 .vop_setextattr = (void *)vop_eopnotsupp,
97 .vop_nresolve = vop_compat_nresolve,
98 .vop_nlookupdotdot = vop_compat_nlookupdotdot,
99 .vop_ncreate = vop_compat_ncreate,
100 .vop_nmkdir = vop_compat_nmkdir,
101 .vop_nmknod = vop_compat_nmknod,
102 .vop_nlink = vop_compat_nlink,
103 .vop_nsymlink = vop_compat_nsymlink,
104 .vop_nwhiteout = vop_compat_nwhiteout,
105 .vop_nremove = vop_compat_nremove,
106 .vop_nrmdir = vop_compat_nrmdir,
107 .vop_nrename = vop_compat_nrename,
108 .vop_mountctl = journal_mountctl
111 VNODEOP_SET(default_vnode_vops);
114 vop_eopnotsupp(struct vop_generic_args *ap)
116 return (EOPNOTSUPP);
120 vop_ebadf(struct vop_generic_args *ap)
122 return (EBADF);
126 vop_enotty(struct vop_generic_args *ap)
128 return (ENOTTY);
132 vop_einval(struct vop_generic_args *ap)
134 return (EINVAL);
138 vop_null(struct vop_generic_args *ap)
140 return (0);
144 vop_defaultop(struct vop_generic_args *ap)
146 return (VOCALL(&default_vnode_vops, ap));
150 vop_panic(struct vop_generic_args *ap)
152 panic("filesystem goof: vop_panic[%s]", ap->a_desc->sd_name);
156 * vop_compat_resolve { struct nchandle *a_nch, struct vnode *dvp }
157 * XXX STOPGAP FUNCTION
159 * XXX OLD API ROUTINE! WHEN ALL VFSs HAVE BEEN CLEANED UP THIS PROCEDURE
160 * WILL BE REMOVED. This procedure exists for all VFSs which have not
161 * yet implemented VOP_NRESOLVE(). It converts VOP_NRESOLVE() into a
162 * vop_old_lookup() and does appropriate translations.
164 * Resolve a ncp for VFSs which do not support the VOP. Eventually all
165 * VFSs will support this VOP and this routine can be removed, since
166 * VOP_NRESOLVE() is far less complex then the older LOOKUP/CACHEDLOOKUP
167 * API.
169 * A locked ncp is passed in to be resolved. The NCP is resolved by
170 * figuring out the vnode (if any) and calling cache_setvp() to attach the
171 * vnode to the entry. If the entry represents a non-existant node then
172 * cache_setvp() is called with a NULL vnode to resolve the entry into a
173 * negative cache entry. No vnode locks are retained and the
174 * ncp is left locked on return.
176 * The ncp will NEVER represent "", "." or "..", or contain any slashes.
178 * There is a potential directory and vnode interlock. The lock order
179 * requirement is: namecache, governing directory, resolved vnode.
182 vop_compat_nresolve(struct vop_nresolve_args *ap)
184 int error;
185 struct vnode *dvp;
186 struct vnode *vp;
187 struct nchandle *nch;
188 struct namecache *ncp;
189 struct componentname cnp;
191 nch = ap->a_nch; /* locked namecache node */
192 ncp = nch->ncp;
193 dvp = ap->a_dvp;
196 * UFS currently stores all sorts of side effects, including a loop
197 * variable, in the directory inode. That needs to be fixed and the
198 * other VFS's audited before we can switch to LK_SHARED.
200 if ((error = vget(dvp, LK_EXCLUSIVE)) != 0) {
201 kprintf("[diagnostic] vop_compat_resolve: EAGAIN on ncp %p %s\n",
202 ncp, ncp->nc_name);
203 return(EAGAIN);
206 bzero(&cnp, sizeof(cnp));
207 cnp.cn_nameiop = NAMEI_LOOKUP;
208 cnp.cn_flags = 0;
209 cnp.cn_nameptr = ncp->nc_name;
210 cnp.cn_namelen = ncp->nc_nlen;
211 cnp.cn_cred = ap->a_cred;
212 cnp.cn_td = curthread; /* XXX */
215 * vop_old_lookup() always returns vp locked. dvp may or may not be
216 * left locked depending on CNP_PDIRUNLOCK.
218 error = vop_old_lookup(ap->a_head.a_ops, dvp, &vp, &cnp);
219 if (error == 0)
220 vn_unlock(vp);
221 if ((cnp.cn_flags & CNP_PDIRUNLOCK) == 0)
222 vn_unlock(dvp);
223 if ((ncp->nc_flag & NCF_UNRESOLVED) == 0) {
224 /* was resolved by another process while we were unlocked */
225 if (error == 0)
226 vrele(vp);
227 } else if (error == 0) {
228 KKASSERT(vp != NULL);
229 cache_setvp(nch, vp);
230 vrele(vp);
231 } else if (error == ENOENT) {
232 KKASSERT(vp == NULL);
233 if (cnp.cn_flags & CNP_ISWHITEOUT)
234 ncp->nc_flag |= NCF_WHITEOUT;
235 cache_setvp(nch, NULL);
237 vrele(dvp);
238 return (error);
242 * vop_compat_nlookupdotdot { struct vnode *a_dvp,
243 * struct vnode **a_vpp,
244 * struct ucred *a_cred }
246 * Lookup the vnode representing the parent directory of the specified
247 * directory vnode. a_dvp should not be locked. If no error occurs *a_vpp
248 * will contained the parent vnode, locked and refd, else *a_vpp will be NULL.
250 * This function is designed to aid NFS server-side operations and is
251 * used by cache_fromdvp() to create a consistent, connected namecache
252 * topology.
254 * As part of the NEW API work, VFSs will first split their CNP_ISDOTDOT
255 * code out from their *_lookup() and create *_nlookupdotdot(). Then as time
256 * permits VFSs will implement the remaining *_n*() calls and finally get
257 * rid of their *_lookup() call.
260 vop_compat_nlookupdotdot(struct vop_nlookupdotdot_args *ap)
262 struct componentname cnp;
263 int error;
266 * UFS currently stores all sorts of side effects, including a loop
267 * variable, in the directory inode. That needs to be fixed and the
268 * other VFS's audited before we can switch to LK_SHARED.
270 *ap->a_vpp = NULL;
271 if ((error = vget(ap->a_dvp, LK_EXCLUSIVE)) != 0)
272 return (error);
273 if (ap->a_dvp->v_type != VDIR) {
274 vput(ap->a_dvp);
275 return (ENOTDIR);
278 bzero(&cnp, sizeof(cnp));
279 cnp.cn_nameiop = NAMEI_LOOKUP;
280 cnp.cn_flags = CNP_ISDOTDOT;
281 cnp.cn_nameptr = "..";
282 cnp.cn_namelen = 2;
283 cnp.cn_cred = ap->a_cred;
284 cnp.cn_td = curthread; /* XXX */
287 * vop_old_lookup() always returns vp locked. dvp may or may not be
288 * left locked depending on CNP_PDIRUNLOCK.
290 error = vop_old_lookup(ap->a_head.a_ops, ap->a_dvp, ap->a_vpp, &cnp);
291 if (error == 0)
292 vn_unlock(*ap->a_vpp);
293 if (cnp.cn_flags & CNP_PDIRUNLOCK)
294 vrele(ap->a_dvp);
295 else
296 vput(ap->a_dvp);
297 return (error);
301 * vop_compat_ncreate { struct nchandle *a_nch, XXX STOPGAP FUNCTION
302 * struct vnode *a_dvp,
303 * struct vnode **a_vpp,
304 * struct ucred *a_cred,
305 * struct vattr *a_vap }
307 * Create a file as specified by a_vap. Compatibility requires us to issue
308 * the appropriate VOP_OLD_LOOKUP before we issue VOP_OLD_CREATE in order
309 * to setup the directory inode's i_offset and i_count (e.g. in UFS).
312 vop_compat_ncreate(struct vop_ncreate_args *ap)
314 struct thread *td = curthread;
315 struct componentname cnp;
316 struct nchandle *nch;
317 struct namecache *ncp;
318 struct vnode *dvp;
319 int error;
322 * Sanity checks, get a locked directory vnode.
324 nch = ap->a_nch; /* locked namecache node */
325 dvp = ap->a_dvp;
326 ncp = nch->ncp;
328 if ((error = vget(dvp, LK_EXCLUSIVE)) != 0) {
329 kprintf("[diagnostic] vop_compat_resolve: EAGAIN on ncp %p %s\n",
330 ncp, ncp->nc_name);
331 return(EAGAIN);
335 * Setup the cnp for a traditional vop_old_lookup() call. The lookup
336 * caches all information required to create the entry in the
337 * directory inode. We expect a return code of EJUSTRETURN for
338 * the CREATE case. The cnp must simulated a saved-name situation.
340 bzero(&cnp, sizeof(cnp));
341 cnp.cn_nameiop = NAMEI_CREATE;
342 cnp.cn_flags = CNP_LOCKPARENT;
343 cnp.cn_nameptr = ncp->nc_name;
344 cnp.cn_namelen = ncp->nc_nlen;
345 cnp.cn_cred = ap->a_cred;
346 cnp.cn_td = td;
347 *ap->a_vpp = NULL;
349 error = vop_old_lookup(ap->a_head.a_ops, dvp, ap->a_vpp, &cnp);
352 * EJUSTRETURN should be returned for this case, which means that
353 * the VFS has setup the directory inode for the create. The dvp we
354 * passed in is expected to remain in a locked state.
356 * If the VOP_OLD_CREATE is successful we are responsible for updating
357 * the cache state of the locked ncp that was passed to us.
359 if (error == EJUSTRETURN) {
360 KKASSERT((cnp.cn_flags & CNP_PDIRUNLOCK) == 0);
361 error = VOP_OLD_CREATE(dvp, ap->a_vpp, &cnp, ap->a_vap);
362 if (error == 0) {
363 cache_setunresolved(nch);
364 cache_setvp(nch, *ap->a_vpp);
366 } else {
367 if (error == 0) {
368 vput(*ap->a_vpp);
369 *ap->a_vpp = NULL;
370 error = EEXIST;
372 KKASSERT(*ap->a_vpp == NULL);
374 if ((cnp.cn_flags & CNP_PDIRUNLOCK) == 0)
375 vn_unlock(dvp);
376 vrele(dvp);
377 return (error);
381 * vop_compat_nmkdir { struct nchandle *a_nch, XXX STOPGAP FUNCTION
382 * struct vnode *a_dvp,
383 * struct vnode **a_vpp,
384 * struct ucred *a_cred,
385 * struct vattr *a_vap }
387 * Create a directory as specified by a_vap. Compatibility requires us to
388 * issue the appropriate VOP_OLD_LOOKUP before we issue VOP_OLD_MKDIR in
389 * order to setup the directory inode's i_offset and i_count (e.g. in UFS).
392 vop_compat_nmkdir(struct vop_nmkdir_args *ap)
394 struct thread *td = curthread;
395 struct componentname cnp;
396 struct nchandle *nch;
397 struct namecache *ncp;
398 struct vnode *dvp;
399 int error;
402 * Sanity checks, get a locked directory vnode.
404 nch = ap->a_nch; /* locked namecache node */
405 ncp = nch->ncp;
406 dvp = ap->a_dvp;
407 if ((error = vget(dvp, LK_EXCLUSIVE)) != 0) {
408 kprintf("[diagnostic] vop_compat_resolve: EAGAIN on ncp %p %s\n",
409 ncp, ncp->nc_name);
410 return(EAGAIN);
414 * Setup the cnp for a traditional vop_old_lookup() call. The lookup
415 * caches all information required to create the entry in the
416 * directory inode. We expect a return code of EJUSTRETURN for
417 * the CREATE case. The cnp must simulated a saved-name situation.
419 bzero(&cnp, sizeof(cnp));
420 cnp.cn_nameiop = NAMEI_CREATE;
421 cnp.cn_flags = CNP_LOCKPARENT;
422 cnp.cn_nameptr = ncp->nc_name;
423 cnp.cn_namelen = ncp->nc_nlen;
424 cnp.cn_cred = ap->a_cred;
425 cnp.cn_td = td;
426 *ap->a_vpp = NULL;
428 error = vop_old_lookup(ap->a_head.a_ops, dvp, ap->a_vpp, &cnp);
431 * EJUSTRETURN should be returned for this case, which means that
432 * the VFS has setup the directory inode for the create. The dvp we
433 * passed in is expected to remain in a locked state.
435 * If the VOP_OLD_MKDIR is successful we are responsible for updating
436 * the cache state of the locked ncp that was passed to us.
438 if (error == EJUSTRETURN) {
439 KKASSERT((cnp.cn_flags & CNP_PDIRUNLOCK) == 0);
440 error = VOP_OLD_MKDIR(dvp, ap->a_vpp, &cnp, ap->a_vap);
441 if (error == 0) {
442 cache_setunresolved(nch);
443 cache_setvp(nch, *ap->a_vpp);
445 } else {
446 if (error == 0) {
447 vput(*ap->a_vpp);
448 *ap->a_vpp = NULL;
449 error = EEXIST;
451 KKASSERT(*ap->a_vpp == NULL);
453 if ((cnp.cn_flags & CNP_PDIRUNLOCK) == 0)
454 vn_unlock(dvp);
455 vrele(dvp);
456 return (error);
460 * vop_compat_nmknod { struct nchandle *a_nch, XXX STOPGAP FUNCTION
461 * struct vnode *a_dvp,
462 * struct vnode **a_vpp,
463 * struct ucred *a_cred,
464 * struct vattr *a_vap }
466 * Create a device or fifo node as specified by a_vap. Compatibility requires
467 * us to issue the appropriate VOP_OLD_LOOKUP before we issue VOP_OLD_MKNOD
468 * in order to setup the directory inode's i_offset and i_count (e.g. in UFS).
471 vop_compat_nmknod(struct vop_nmknod_args *ap)
473 struct thread *td = curthread;
474 struct componentname cnp;
475 struct nchandle *nch;
476 struct namecache *ncp;
477 struct vnode *dvp;
478 int error;
481 * Sanity checks, get a locked directory vnode.
483 nch = ap->a_nch; /* locked namecache node */
484 ncp = nch->ncp;
485 dvp = ap->a_dvp;
487 if ((error = vget(dvp, LK_EXCLUSIVE)) != 0) {
488 kprintf("[diagnostic] vop_compat_resolve: EAGAIN on ncp %p %s\n",
489 ncp, ncp->nc_name);
490 return(EAGAIN);
494 * Setup the cnp for a traditional vop_old_lookup() call. The lookup
495 * caches all information required to create the entry in the
496 * directory inode. We expect a return code of EJUSTRETURN for
497 * the CREATE case. The cnp must simulated a saved-name situation.
499 bzero(&cnp, sizeof(cnp));
500 cnp.cn_nameiop = NAMEI_CREATE;
501 cnp.cn_flags = CNP_LOCKPARENT;
502 cnp.cn_nameptr = ncp->nc_name;
503 cnp.cn_namelen = ncp->nc_nlen;
504 cnp.cn_cred = ap->a_cred;
505 cnp.cn_td = td;
506 *ap->a_vpp = NULL;
508 error = vop_old_lookup(ap->a_head.a_ops, dvp, ap->a_vpp, &cnp);
511 * EJUSTRETURN should be returned for this case, which means that
512 * the VFS has setup the directory inode for the create. The dvp we
513 * passed in is expected to remain in a locked state.
515 * If the VOP_OLD_MKNOD is successful we are responsible for updating
516 * the cache state of the locked ncp that was passed to us.
518 if (error == EJUSTRETURN) {
519 KKASSERT((cnp.cn_flags & CNP_PDIRUNLOCK) == 0);
520 error = VOP_OLD_MKNOD(dvp, ap->a_vpp, &cnp, ap->a_vap);
521 if (error == 0) {
522 cache_setunresolved(nch);
523 cache_setvp(nch, *ap->a_vpp);
525 } else {
526 if (error == 0) {
527 vput(*ap->a_vpp);
528 *ap->a_vpp = NULL;
529 error = EEXIST;
531 KKASSERT(*ap->a_vpp == NULL);
533 if ((cnp.cn_flags & CNP_PDIRUNLOCK) == 0)
534 vn_unlock(dvp);
535 vrele(dvp);
536 return (error);
540 * vop_compat_nlink { struct nchandle *a_nch, XXX STOPGAP FUNCTION
541 * struct vnode *a_dvp,
542 * struct vnode *a_vp,
543 * struct ucred *a_cred }
545 * The passed vp is locked and represents the source. The passed ncp is
546 * locked and represents the target to create.
549 vop_compat_nlink(struct vop_nlink_args *ap)
551 struct thread *td = curthread;
552 struct componentname cnp;
553 struct nchandle *nch;
554 struct namecache *ncp;
555 struct vnode *dvp;
556 struct vnode *tvp;
557 int error;
560 * Sanity checks, get a locked directory vnode.
562 nch = ap->a_nch; /* locked namecache node */
563 ncp = nch->ncp;
564 dvp = ap->a_dvp;
566 if ((error = vget(dvp, LK_EXCLUSIVE)) != 0) {
567 kprintf("[diagnostic] vop_compat_resolve: EAGAIN on ncp %p %s\n",
568 ncp, ncp->nc_name);
569 return(EAGAIN);
573 * Setup the cnp for a traditional vop_old_lookup() call. The lookup
574 * caches all information required to create the entry in the
575 * directory inode. We expect a return code of EJUSTRETURN for
576 * the CREATE case. The cnp must simulated a saved-name situation.
578 bzero(&cnp, sizeof(cnp));
579 cnp.cn_nameiop = NAMEI_CREATE;
580 cnp.cn_flags = CNP_LOCKPARENT;
581 cnp.cn_nameptr = ncp->nc_name;
582 cnp.cn_namelen = ncp->nc_nlen;
583 cnp.cn_cred = ap->a_cred;
584 cnp.cn_td = td;
586 tvp = NULL;
587 error = vop_old_lookup(ap->a_head.a_ops, dvp, &tvp, &cnp);
590 * EJUSTRETURN should be returned for this case, which means that
591 * the VFS has setup the directory inode for the create. The dvp we
592 * passed in is expected to remain in a locked state.
594 * If the VOP_OLD_LINK is successful we are responsible for updating
595 * the cache state of the locked ncp that was passed to us.
597 if (error == EJUSTRETURN) {
598 KKASSERT((cnp.cn_flags & CNP_PDIRUNLOCK) == 0);
599 error = VOP_OLD_LINK(dvp, ap->a_vp, &cnp);
600 if (error == 0) {
601 cache_setunresolved(nch);
602 cache_setvp(nch, ap->a_vp);
604 } else {
605 if (error == 0) {
606 vput(tvp);
607 error = EEXIST;
610 if ((cnp.cn_flags & CNP_PDIRUNLOCK) == 0)
611 vn_unlock(dvp);
612 vrele(dvp);
613 return (error);
617 vop_compat_nsymlink(struct vop_nsymlink_args *ap)
619 struct thread *td = curthread;
620 struct componentname cnp;
621 struct nchandle *nch;
622 struct namecache *ncp;
623 struct vnode *dvp;
624 struct vnode *vp;
625 int error;
628 * Sanity checks, get a locked directory vnode.
630 *ap->a_vpp = NULL;
631 nch = ap->a_nch; /* locked namecache node */
632 ncp = nch->ncp;
633 dvp = ap->a_dvp;
635 if ((error = vget(dvp, LK_EXCLUSIVE)) != 0) {
636 kprintf("[diagnostic] vop_compat_resolve: EAGAIN on ncp %p %s\n",
637 ncp, ncp->nc_name);
638 return(EAGAIN);
642 * Setup the cnp for a traditional vop_old_lookup() call. The lookup
643 * caches all information required to create the entry in the
644 * directory inode. We expect a return code of EJUSTRETURN for
645 * the CREATE case. The cnp must simulated a saved-name situation.
647 bzero(&cnp, sizeof(cnp));
648 cnp.cn_nameiop = NAMEI_CREATE;
649 cnp.cn_flags = CNP_LOCKPARENT;
650 cnp.cn_nameptr = ncp->nc_name;
651 cnp.cn_namelen = ncp->nc_nlen;
652 cnp.cn_cred = ap->a_cred;
653 cnp.cn_td = td;
655 vp = NULL;
656 error = vop_old_lookup(ap->a_head.a_ops, dvp, &vp, &cnp);
659 * EJUSTRETURN should be returned for this case, which means that
660 * the VFS has setup the directory inode for the create. The dvp we
661 * passed in is expected to remain in a locked state.
663 * If the VOP_OLD_SYMLINK is successful we are responsible for updating
664 * the cache state of the locked ncp that was passed to us.
666 if (error == EJUSTRETURN) {
667 KKASSERT((cnp.cn_flags & CNP_PDIRUNLOCK) == 0);
668 error = VOP_OLD_SYMLINK(dvp, &vp, &cnp, ap->a_vap, ap->a_target);
669 if (error == 0) {
670 cache_setunresolved(nch);
671 cache_setvp(nch, vp);
672 *ap->a_vpp = vp;
674 } else {
675 if (error == 0) {
676 vput(vp);
677 vp = NULL;
678 error = EEXIST;
680 KKASSERT(vp == NULL);
682 if ((cnp.cn_flags & CNP_PDIRUNLOCK) == 0)
683 vn_unlock(dvp);
684 vrele(dvp);
685 return (error);
689 * vop_compat_nwhiteout { struct nchandle *a_nch, XXX STOPGAP FUNCTION
690 * struct vnode *a_dvp,
691 * struct ucred *a_cred,
692 * int a_flags }
694 * Issie a whiteout operation (create, lookup, or delete). Compatibility
695 * requires us to issue the appropriate VOP_OLD_LOOKUP before we issue
696 * VOP_OLD_WHITEOUT in order to setup the directory inode's i_offset and i_count
697 * (e.g. in UFS) for the NAMEI_CREATE and NAMEI_DELETE ops. For NAMEI_LOOKUP
698 * no lookup is necessary.
701 vop_compat_nwhiteout(struct vop_nwhiteout_args *ap)
703 struct thread *td = curthread;
704 struct componentname cnp;
705 struct nchandle *nch;
706 struct namecache *ncp;
707 struct vnode *dvp;
708 struct vnode *vp;
709 int error;
712 * Sanity checks, get a locked directory vnode.
714 nch = ap->a_nch; /* locked namecache node */
715 ncp = nch->ncp;
716 dvp = ap->a_dvp;
718 if ((error = vget(dvp, LK_EXCLUSIVE)) != 0) {
719 kprintf("[diagnostic] vop_compat_resolve: EAGAIN on ncp %p %s\n",
720 ncp, ncp->nc_name);
721 return(EAGAIN);
725 * Setup the cnp for a traditional vop_old_lookup() call. The lookup
726 * caches all information required to create the entry in the
727 * directory inode. We expect a return code of EJUSTRETURN for
728 * the CREATE case. The cnp must simulated a saved-name situation.
730 bzero(&cnp, sizeof(cnp));
731 cnp.cn_nameiop = ap->a_flags;
732 cnp.cn_flags = CNP_LOCKPARENT;
733 cnp.cn_nameptr = ncp->nc_name;
734 cnp.cn_namelen = ncp->nc_nlen;
735 cnp.cn_cred = ap->a_cred;
736 cnp.cn_td = td;
738 vp = NULL;
741 * EJUSTRETURN should be returned for the CREATE or DELETE cases.
742 * The VFS has setup the directory inode for the create. The dvp we
743 * passed in is expected to remain in a locked state.
745 * If the VOP_OLD_WHITEOUT is successful we are responsible for updating
746 * the cache state of the locked ncp that was passed to us.
748 switch(ap->a_flags) {
749 case NAMEI_DELETE:
750 cnp.cn_flags |= CNP_DOWHITEOUT;
751 /* fall through */
752 case NAMEI_CREATE:
753 error = vop_old_lookup(ap->a_head.a_ops, dvp, &vp, &cnp);
754 if (error == EJUSTRETURN) {
755 KKASSERT((cnp.cn_flags & CNP_PDIRUNLOCK) == 0);
756 error = VOP_OLD_WHITEOUT(dvp, &cnp, ap->a_flags);
757 if (error == 0)
758 cache_setunresolved(nch);
759 } else {
760 if (error == 0) {
761 vput(vp);
762 vp = NULL;
763 error = EEXIST;
765 KKASSERT(vp == NULL);
767 break;
768 case NAMEI_LOOKUP:
769 error = VOP_OLD_WHITEOUT(dvp, NULL, ap->a_flags);
770 break;
771 default:
772 error = EINVAL;
773 break;
775 if ((cnp.cn_flags & CNP_PDIRUNLOCK) == 0)
776 vn_unlock(dvp);
777 vrele(dvp);
778 return (error);
783 * vop_compat_nremove { struct nchandle *a_nch, XXX STOPGAP FUNCTION
784 * struct vnode *a_dvp,
785 * struct ucred *a_cred }
788 vop_compat_nremove(struct vop_nremove_args *ap)
790 struct thread *td = curthread;
791 struct componentname cnp;
792 struct nchandle *nch;
793 struct namecache *ncp;
794 struct vnode *dvp;
795 struct vnode *vp;
796 int error;
799 * Sanity checks, get a locked directory vnode.
801 nch = ap->a_nch; /* locked namecache node */
802 ncp = nch->ncp;
803 dvp = ap->a_dvp;
805 if ((error = vget(dvp, LK_EXCLUSIVE)) != 0) {
806 kprintf("[diagnostic] vop_compat_resolve: EAGAIN on ncp %p %s\n",
807 ncp, ncp->nc_name);
808 return(EAGAIN);
812 * Setup the cnp for a traditional vop_old_lookup() call. The lookup
813 * caches all information required to delete the entry in the
814 * directory inode. We expect a return code of 0 for the DELETE
815 * case (meaning that a vp has been found). The cnp must simulated
816 * a saved-name situation.
818 bzero(&cnp, sizeof(cnp));
819 cnp.cn_nameiop = NAMEI_DELETE;
820 cnp.cn_flags = CNP_LOCKPARENT;
821 cnp.cn_nameptr = ncp->nc_name;
822 cnp.cn_namelen = ncp->nc_nlen;
823 cnp.cn_cred = ap->a_cred;
824 cnp.cn_td = td;
827 * The vnode must be a directory and must not represent the
828 * current directory.
830 vp = NULL;
831 error = vop_old_lookup(ap->a_head.a_ops, dvp, &vp, &cnp);
832 if (error == 0 && vp->v_type == VDIR)
833 error = EPERM;
834 if (error == 0) {
835 KKASSERT((cnp.cn_flags & CNP_PDIRUNLOCK) == 0);
836 error = VOP_OLD_REMOVE(dvp, vp, &cnp);
837 if (error == 0) {
838 cache_setunresolved(nch);
839 cache_setvp(nch, NULL);
840 cache_inval_vp(vp, CINV_DESTROY);
843 if (vp) {
844 if (dvp == vp)
845 vrele(vp);
846 else
847 vput(vp);
849 if ((cnp.cn_flags & CNP_PDIRUNLOCK) == 0)
850 vn_unlock(dvp);
851 vrele(dvp);
852 return (error);
856 * vop_compat_nrmdir { struct nchandle *a_nch, XXX STOPGAP FUNCTION
857 * struct vnode *dvp,
858 * struct ucred *a_cred }
861 vop_compat_nrmdir(struct vop_nrmdir_args *ap)
863 struct thread *td = curthread;
864 struct componentname cnp;
865 struct nchandle *nch;
866 struct namecache *ncp;
867 struct vnode *dvp;
868 struct vnode *vp;
869 int error;
872 * Sanity checks, get a locked directory vnode.
874 nch = ap->a_nch; /* locked namecache node */
875 ncp = nch->ncp;
876 dvp = ap->a_dvp;
878 if ((error = vget(dvp, LK_EXCLUSIVE)) != 0) {
879 kprintf("[diagnostic] vop_compat_resolve: EAGAIN on ncp %p %s\n",
880 ncp, ncp->nc_name);
881 return(EAGAIN);
885 * Setup the cnp for a traditional vop_old_lookup() call. The lookup
886 * caches all information required to delete the entry in the
887 * directory inode. We expect a return code of 0 for the DELETE
888 * case (meaning that a vp has been found). The cnp must simulated
889 * a saved-name situation.
891 bzero(&cnp, sizeof(cnp));
892 cnp.cn_nameiop = NAMEI_DELETE;
893 cnp.cn_flags = CNP_LOCKPARENT;
894 cnp.cn_nameptr = ncp->nc_name;
895 cnp.cn_namelen = ncp->nc_nlen;
896 cnp.cn_cred = ap->a_cred;
897 cnp.cn_td = td;
900 * The vnode must be a directory and must not represent the
901 * current directory.
903 vp = NULL;
904 error = vop_old_lookup(ap->a_head.a_ops, dvp, &vp, &cnp);
905 if (error == 0 && vp->v_type != VDIR)
906 error = ENOTDIR;
907 if (error == 0 && vp == dvp)
908 error = EINVAL;
909 if (error == 0 && (vp->v_flag & VROOT))
910 error = EBUSY;
911 if (error == 0) {
912 KKASSERT((cnp.cn_flags & CNP_PDIRUNLOCK) == 0);
913 error = VOP_OLD_RMDIR(dvp, vp, &cnp);
916 * Note that this invalidation will cause any process
917 * currently CD'd into the directory being removed to be
918 * disconnected from the topology and not be able to ".."
919 * back out.
921 if (error == 0) {
922 cache_inval(nch, CINV_DESTROY);
923 cache_inval_vp(vp, CINV_DESTROY);
926 if (vp) {
927 if (dvp == vp)
928 vrele(vp);
929 else
930 vput(vp);
932 if ((cnp.cn_flags & CNP_PDIRUNLOCK) == 0)
933 vn_unlock(dvp);
934 vrele(dvp);
935 return (error);
939 * vop_compat_nrename { struct nchandle *a_fnch, XXX STOPGAP FUNCTION
940 * struct nchandle *a_tnch,
941 * struct ucred *a_cred }
943 * This is a fairly difficult procedure. The old VOP_OLD_RENAME requires that
944 * the source directory and vnode be unlocked and the target directory and
945 * vnode (if it exists) be locked. All arguments will be vrele'd and
946 * the targets will also be unlocked regardless of the return code.
949 vop_compat_nrename(struct vop_nrename_args *ap)
951 struct thread *td = curthread;
952 struct componentname fcnp;
953 struct componentname tcnp;
954 struct nchandle *fnch;
955 struct nchandle *tnch;
956 struct namecache *fncp;
957 struct namecache *tncp;
958 struct vnode *fdvp, *fvp;
959 struct vnode *tdvp, *tvp;
960 int error;
963 * Sanity checks, get referenced vnodes representing the source.
965 fnch = ap->a_fnch; /* locked namecache node */
966 fncp = fnch->ncp;
967 fdvp = ap->a_fdvp;
970 * Temporarily lock the source directory and lookup in DELETE mode to
971 * check permissions. XXX delete permissions should have been
972 * checked by nlookup(), we need to add NLC_DELETE for delete
973 * checking. It is unclear whether VFS's require the directory setup
974 * info NAMEI_DELETE causes to be stored in the fdvp's inode, but
975 * since it isn't locked and since UFS always does a relookup of
976 * the source, it is believed that the only side effect that matters
977 * is the permissions check.
979 if ((error = vget(fdvp, LK_EXCLUSIVE)) != 0) {
980 kprintf("[diagnostic] vop_compat_resolve: EAGAIN on ncp %p %s\n",
981 fncp, fncp->nc_name);
982 return(EAGAIN);
985 bzero(&fcnp, sizeof(fcnp));
986 fcnp.cn_nameiop = NAMEI_DELETE;
987 fcnp.cn_flags = CNP_LOCKPARENT;
988 fcnp.cn_nameptr = fncp->nc_name;
989 fcnp.cn_namelen = fncp->nc_nlen;
990 fcnp.cn_cred = ap->a_cred;
991 fcnp.cn_td = td;
994 * note: vop_old_lookup (i.e. VOP_OLD_LOOKUP) always returns a locked
995 * fvp.
997 fvp = NULL;
998 error = vop_old_lookup(ap->a_head.a_ops, fdvp, &fvp, &fcnp);
999 if (error == 0 && (fvp->v_flag & VROOT)) {
1000 vput(fvp); /* as if vop_old_lookup had failed */
1001 error = EBUSY;
1003 if ((fcnp.cn_flags & CNP_PDIRUNLOCK) == 0) {
1004 fcnp.cn_flags |= CNP_PDIRUNLOCK;
1005 vn_unlock(fdvp);
1007 if (error) {
1008 vrele(fdvp);
1009 return (error);
1011 vn_unlock(fvp);
1014 * fdvp and fvp are now referenced and unlocked.
1016 * Get a locked directory vnode for the target and lookup the target
1017 * in CREATE mode so it places the required information in the
1018 * directory inode.
1020 tnch = ap->a_tnch; /* locked namecache node */
1021 tncp = tnch->ncp;
1022 tdvp = ap->a_tdvp;
1023 if (error) {
1024 vrele(fdvp);
1025 vrele(fvp);
1026 return (error);
1028 if ((error = vget(tdvp, LK_EXCLUSIVE)) != 0) {
1029 kprintf("[diagnostic] vop_compat_resolve: EAGAIN on ncp %p %s\n",
1030 tncp, tncp->nc_name);
1031 vrele(fdvp);
1032 vrele(fvp);
1033 return(EAGAIN);
1037 * Setup the cnp for a traditional vop_old_lookup() call. The lookup
1038 * caches all information required to create the entry in the
1039 * target directory inode.
1041 bzero(&tcnp, sizeof(tcnp));
1042 tcnp.cn_nameiop = NAMEI_RENAME;
1043 tcnp.cn_flags = CNP_LOCKPARENT;
1044 tcnp.cn_nameptr = tncp->nc_name;
1045 tcnp.cn_namelen = tncp->nc_nlen;
1046 tcnp.cn_cred = ap->a_cred;
1047 tcnp.cn_td = td;
1049 tvp = NULL;
1050 error = vop_old_lookup(ap->a_head.a_ops, tdvp, &tvp, &tcnp);
1052 if (error == EJUSTRETURN) {
1054 * Target does not exist. tvp should be NULL.
1056 KKASSERT(tvp == NULL);
1057 KKASSERT((tcnp.cn_flags & CNP_PDIRUNLOCK) == 0);
1058 error = VOP_OLD_RENAME(fdvp, fvp, &fcnp, tdvp, tvp, &tcnp);
1059 if (error == 0)
1060 cache_rename(fnch, tnch);
1061 } else if (error == 0) {
1063 * Target exists. VOP_OLD_RENAME should correctly delete the
1064 * target.
1066 KKASSERT((tcnp.cn_flags & CNP_PDIRUNLOCK) == 0);
1067 error = VOP_OLD_RENAME(fdvp, fvp, &fcnp, tdvp, tvp, &tcnp);
1068 if (error == 0)
1069 cache_rename(fnch, tnch);
1070 } else {
1071 vrele(fdvp);
1072 vrele(fvp);
1073 if (tcnp.cn_flags & CNP_PDIRUNLOCK)
1074 vrele(tdvp);
1075 else
1076 vput(tdvp);
1078 return (error);
1081 static int
1082 vop_nolookup(struct vop_old_lookup_args *ap)
1085 *ap->a_vpp = NULL;
1086 return (ENOTDIR);
1090 * vop_nostrategy:
1092 * Strategy routine for VFS devices that have none.
1094 * B_ERROR and B_INVAL must be cleared prior to calling any strategy
1095 * routine. Typically this is done for a BUF_CMD_READ strategy call.
1096 * Typically B_INVAL is assumed to already be clear prior to a write
1097 * and should not be cleared manually unless you just made the buffer
1098 * invalid. B_ERROR should be cleared either way.
1101 static int
1102 vop_nostrategy (struct vop_strategy_args *ap)
1104 kprintf("No strategy for buffer at %p\n", ap->a_bio->bio_buf);
1105 vprint("", ap->a_vp);
1106 ap->a_bio->bio_buf->b_flags |= B_ERROR;
1107 ap->a_bio->bio_buf->b_error = EOPNOTSUPP;
1108 biodone(ap->a_bio);
1109 return (EOPNOTSUPP);
1113 vop_stdpathconf(struct vop_pathconf_args *ap)
1116 switch (ap->a_name) {
1117 case _PC_LINK_MAX:
1118 *ap->a_retval = LINK_MAX;
1119 return (0);
1120 case _PC_MAX_CANON:
1121 *ap->a_retval = MAX_CANON;
1122 return (0);
1123 case _PC_MAX_INPUT:
1124 *ap->a_retval = MAX_INPUT;
1125 return (0);
1126 case _PC_PIPE_BUF:
1127 *ap->a_retval = PIPE_BUF;
1128 return (0);
1129 case _PC_CHOWN_RESTRICTED:
1130 *ap->a_retval = 1;
1131 return (0);
1132 case _PC_VDISABLE:
1133 *ap->a_retval = _POSIX_VDISABLE;
1134 return (0);
1135 default:
1136 return (EINVAL);
1138 /* NOTREACHED */
1142 * Standard open.
1144 * (struct vnode *a_vp, int a_mode, struct ucred *a_ucred, struct file *a_fp)
1146 * a_mode: note, 'F' modes, e.g. FREAD, FWRITE
1149 vop_stdopen(struct vop_open_args *ap)
1151 struct vnode *vp = ap->a_vp;
1152 struct file *fp;
1154 if ((fp = ap->a_fp) != NULL) {
1155 switch(vp->v_type) {
1156 case VFIFO:
1157 fp->f_type = DTYPE_FIFO;
1158 break;
1159 default:
1160 fp->f_type = DTYPE_VNODE;
1161 break;
1163 fp->f_flag = ap->a_mode & FMASK;
1164 fp->f_ops = &vnode_fileops;
1165 fp->f_data = vp;
1166 vref(vp);
1168 if (ap->a_mode & FWRITE)
1169 ++vp->v_writecount;
1170 KKASSERT(vp->v_opencount >= 0 && vp->v_opencount != INT_MAX);
1171 ++vp->v_opencount;
1172 return (0);
1176 * Standard close.
1178 * (struct vnode *a_vp, int a_fflag)
1180 * a_fflag: note, 'F' modes, e.g. FREAD, FWRITE. same as a_mode in stdopen?
1183 vop_stdclose(struct vop_close_args *ap)
1185 struct vnode *vp = ap->a_vp;
1187 KASSERT(vp->v_opencount > 0,
1188 ("VOP_STDCLOSE: BAD OPENCOUNT %p %d type=%d ops=%p flgs=%08x\n",
1189 vp, vp->v_opencount, vp->v_type, *vp->v_ops, vp->v_flag));
1190 if (ap->a_fflag & FWRITE) {
1191 KASSERT(vp->v_writecount > 0,
1192 ("VOP_STDCLOSE: BAD WRITECOUNT %p %d\n",
1193 vp, vp->v_writecount));
1194 --vp->v_writecount;
1196 --vp->v_opencount;
1197 return (0);
1201 * Return true for select/poll.
1204 vop_nopoll(struct vop_poll_args *ap)
1207 * Return true for read/write. If the user asked for something
1208 * special, return POLLNVAL, so that clients have a way of
1209 * determining reliably whether or not the extended
1210 * functionality is present without hard-coding knowledge
1211 * of specific filesystem implementations.
1213 if (ap->a_events & ~POLLSTANDARD)
1214 return (POLLNVAL);
1216 return (ap->a_events & (POLLIN | POLLOUT | POLLRDNORM | POLLWRNORM));
1220 * Implement poll for local filesystems that support it.
1223 vop_stdpoll(struct vop_poll_args *ap)
1225 if (ap->a_events & ~POLLSTANDARD)
1226 return (vn_pollrecord(ap->a_vp, ap->a_events));
1227 return (ap->a_events & (POLLIN | POLLOUT | POLLRDNORM | POLLWRNORM));
1231 * Implement standard getpages and putpages. All filesystems must use
1232 * the buffer cache to back regular files.
1235 vop_stdgetpages(struct vop_getpages_args *ap)
1237 struct mount *mp;
1238 int error;
1240 if ((mp = ap->a_vp->v_mount) != NULL) {
1241 error = vnode_pager_generic_getpages(
1242 ap->a_vp, ap->a_m, ap->a_count,
1243 ap->a_reqpage);
1244 } else {
1245 error = VM_PAGER_BAD;
1247 return (error);
1251 vop_stdputpages(struct vop_putpages_args *ap)
1253 struct mount *mp;
1254 int error;
1256 if ((mp = ap->a_vp->v_mount) != NULL) {
1257 error = vnode_pager_generic_putpages(
1258 ap->a_vp, ap->a_m, ap->a_count,
1259 ap->a_sync, ap->a_rtvals);
1260 } else {
1261 error = VM_PAGER_BAD;
1263 return (error);
1267 * vfs default ops
1268 * used to fill the vfs fucntion table to get reasonable default return values.
1270 int
1271 vfs_stdmount(struct mount *mp, char *path, caddr_t data, struct ucred *cred)
1273 return (0);
1276 int
1277 vfs_stdunmount(struct mount *mp, int mntflags)
1279 return (0);
1282 int
1283 vfs_stdroot(struct mount *mp, struct vnode **vpp)
1285 return (EOPNOTSUPP);
1288 int
1289 vfs_stdstatfs(struct mount *mp, struct statfs *sbp, struct ucred *cred)
1291 return (EOPNOTSUPP);
1295 vfs_stdvptofh(struct vnode *vp, struct fid *fhp)
1297 return (EOPNOTSUPP);
1300 int
1301 vfs_stdstart(struct mount *mp, int flags)
1303 return (0);
1306 int
1307 vfs_stdquotactl(struct mount *mp, int cmds, uid_t uid,
1308 caddr_t arg, struct ucred *cred)
1310 return (EOPNOTSUPP);
1313 int
1314 vfs_stdsync(struct mount *mp, int waitfor)
1316 return (0);
1320 vfs_stdnosync(struct mount *mp, int waitfor)
1322 return (EOPNOTSUPP);
1325 int
1326 vfs_stdvget(struct mount *mp, ino_t ino, struct vnode **vpp)
1328 return (EOPNOTSUPP);
1331 int
1332 vfs_stdfhtovp(struct mount *mp, struct fid *fhp, struct vnode **vpp)
1334 return (EOPNOTSUPP);
1337 int
1338 vfs_stdcheckexp(struct mount *mp, struct sockaddr *nam, int *extflagsp,
1339 struct ucred **credanonp)
1341 return (EOPNOTSUPP);
1345 vfs_stdinit(struct vfsconf *vfsp)
1347 return (0);
1351 vfs_stduninit(struct vfsconf *vfsp)
1353 return(0);
1357 vfs_stdextattrctl(struct mount *mp, int cmd, const char *attrname,
1358 caddr_t arg, struct ucred *cred)
1360 return(EOPNOTSUPP);
1363 /* end of vfs default ops */