Annotation of src/sys/kern/vfs_init.c, Revision 1.23.2.6
1.23.2.6! skrll 1: /* $NetBSD: vfs_init.c,v 1.23.2.5 2005/04/01 14:30:57 skrll Exp $ */
1.9 thorpej 2:
3: /*-
1.16 thorpej 4: * Copyright (c) 1998, 2000 The NetBSD Foundation, Inc.
1.9 thorpej 5: * All rights reserved.
6: *
7: * This code is derived from software contributed to The NetBSD Foundation
8: * by Jason R. Thorpe of the Numerical Aerospace Simulation Facility,
9: * NASA Ames Research Center.
10: *
11: * Redistribution and use in source and binary forms, with or without
12: * modification, are permitted provided that the following conditions
13: * are met:
14: * 1. Redistributions of source code must retain the above copyright
15: * notice, this list of conditions and the following disclaimer.
16: * 2. Redistributions in binary form must reproduce the above copyright
17: * notice, this list of conditions and the following disclaimer in the
18: * documentation and/or other materials provided with the distribution.
19: * 3. All advertising materials mentioning features or use of this software
20: * must display the following acknowledgement:
21: * This product includes software developed by the NetBSD
22: * Foundation, Inc. and its contributors.
23: * 4. Neither the name of The NetBSD Foundation nor the names of its
24: * contributors may be used to endorse or promote products derived
25: * from this software without specific prior written permission.
26: *
27: * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
28: * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
29: * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
30: * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
31: * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
32: * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
33: * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
34: * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
35: * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
36: * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
37: * POSSIBILITY OF SUCH DAMAGE.
38: */
1.2 cgd 39:
1.1 mycroft 40: /*
41: * Copyright (c) 1989, 1993
42: * The Regents of the University of California. All rights reserved.
43: *
44: * This code is derived from software contributed
45: * to Berkeley by John Heidemann of the UCLA Ficus project.
46: *
47: * Source: * @(#)i405_init.c 2.10 92/04/27 UCLA Ficus project
48: *
49: * Redistribution and use in source and binary forms, with or without
50: * modification, are permitted provided that the following conditions
51: * are met:
52: * 1. Redistributions of source code must retain the above copyright
53: * notice, this list of conditions and the following disclaimer.
54: * 2. Redistributions in binary form must reproduce the above copyright
55: * notice, this list of conditions and the following disclaimer in the
56: * documentation and/or other materials provided with the distribution.
1.23.2.1 skrll 57: * 3. Neither the name of the University nor the names of its contributors
1.1 mycroft 58: * may be used to endorse or promote products derived from this software
59: * without specific prior written permission.
60: *
61: * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
62: * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
63: * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
64: * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
65: * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
66: * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
67: * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
68: * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
69: * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
70: * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
71: * SUCH DAMAGE.
72: *
1.10 fvdl 73: * @(#)vfs_init.c 8.5 (Berkeley) 5/11/95
1.1 mycroft 74: */
1.20 lukem 75:
76: #include <sys/cdefs.h>
1.23.2.6! skrll 77: __KERNEL_RCSID(0, "$NetBSD: vfs_init.c,v 1.23.2.5 2005/04/01 14:30:57 skrll Exp $");
1.1 mycroft 78:
79: #include <sys/param.h>
80: #include <sys/mount.h>
81: #include <sys/time.h>
82: #include <sys/vnode.h>
83: #include <sys/stat.h>
84: #include <sys/namei.h>
85: #include <sys/ucred.h>
86: #include <sys/buf.h>
87: #include <sys/errno.h>
88: #include <sys/malloc.h>
1.5 christos 89: #include <sys/systm.h>
1.1 mycroft 90:
91: /*
92: * Sigh, such primitive tools are these...
93: */
94: #if 0
95: #define DODEBUG(A) A
96: #else
97: #define DODEBUG(A)
98: #endif
99:
1.9 thorpej 100: /*
101: * The global list of vnode operations.
102: */
1.17 jdolecek 103: extern const struct vnodeop_desc * const vfs_op_descs[];
1.9 thorpej 104:
105: /*
106: * These vnodeopv_descs are listed here because they are not
107: * associated with any particular file system, and thus cannot
108: * be initialized by vfs_attach().
109: */
1.18 jdolecek 110: extern const struct vnodeopv_desc dead_vnodeop_opv_desc;
111: extern const struct vnodeopv_desc fifo_vnodeop_opv_desc;
112: extern const struct vnodeopv_desc spec_vnodeop_opv_desc;
113: extern const struct vnodeopv_desc sync_vnodeop_opv_desc;
1.9 thorpej 114:
1.18 jdolecek 115: const struct vnodeopv_desc * const vfs_special_vnodeopv_descs[] = {
1.9 thorpej 116: &dead_vnodeop_opv_desc,
117: &fifo_vnodeop_opv_desc,
118: &spec_vnodeop_opv_desc,
1.15 fvdl 119: &sync_vnodeop_opv_desc,
1.9 thorpej 120: NULL,
121: };
122:
1.1 mycroft 123: /*
124: * This code doesn't work if the defn is **vnodop_defns with cc.
125: * The problem is because of the compiler sometimes putting in an
126: * extra level of indirection for arrays. It's an interesting
127: * "feature" of C.
128: */
1.23.2.1 skrll 129: typedef int (*PFI)(void *);
1.5 christos 130:
1.1 mycroft 131: /*
132: * A miscellaneous routine.
133: * A generic "default" routine that just returns an error.
134: */
1.5 christos 135: /*ARGSUSED*/
1.1 mycroft 136: int
1.23.2.6! skrll 137: vn_default_error(void *v)
1.1 mycroft 138: {
139:
140: return (EOPNOTSUPP);
141: }
142:
143: /*
144: * vfs_init.c
145: *
146: * Allocate and fill in operations vectors.
147: *
148: * An undocumented feature of this approach to defining operations is that
149: * there can be multiple entries in vfs_opv_descs for the same operations
150: * vector. This allows third parties to extend the set of operations
151: * supported by another layer in a binary compatibile way. For example,
152: * assume that NFS needed to be modified to support Ficus. NFS has an entry
153: * (probably nfs_vnopdeop_decls) declaring all the operations NFS supports by
154: * default. Ficus could add another entry (ficus_nfs_vnodeop_decl_entensions)
155: * listing those new operations Ficus adds to NFS, all without modifying the
156: * NFS code. (Of couse, the OTW NFS protocol still needs to be munged, but
157: * that is a(whole)nother story.) This is a feature.
158: */
1.3 mycroft 159:
160: /*
1.9 thorpej 161: * Init the vector, if it needs it.
1.3 mycroft 162: * Also handle backwards compatibility.
163: */
1.17 jdolecek 164: static void
1.23.2.6! skrll 165: vfs_opv_init_explicit(const struct vnodeopv_desc *vfs_opv_desc)
1.1 mycroft 166: {
1.23.2.1 skrll 167: int (**opv_desc_vector)(void *);
1.18 jdolecek 168: const struct vnodeopv_entry_desc *opve_descp;
1.1 mycroft 169:
1.3 mycroft 170: opv_desc_vector = *(vfs_opv_desc->opv_desc_vector_p);
171:
172: for (opve_descp = vfs_opv_desc->opv_desc_ops;
173: opve_descp->opve_op;
174: opve_descp++) {
1.1 mycroft 175: /*
1.3 mycroft 176: * Sanity check: is this operation listed
177: * in the list of operations? We check this
1.23 mjl 178: * by seeing if its offset is zero. Since
1.3 mycroft 179: * the default routine should always be listed
180: * first, it should be the only one with a zero
181: * offset. Any other operation with a zero
182: * offset is probably not listed in
183: * vfs_op_descs, and so is probably an error.
184: *
185: * A panic here means the layer programmer
186: * has committed the all-too common bug
187: * of adding a new operation to the layer's
188: * list of vnode operations but
189: * not adding the operation to the system-wide
190: * list of supported operations.
1.1 mycroft 191: */
1.3 mycroft 192: if (opve_descp->opve_op->vdesc_offset == 0 &&
193: opve_descp->opve_op->vdesc_offset != VOFFSET(vop_default)) {
1.8 christos 194: printf("operation %s not listed in %s.\n",
1.3 mycroft 195: opve_descp->opve_op->vdesc_name, "vfs_op_descs");
196: panic ("vfs_opv_init: bad operation");
1.1 mycroft 197: }
1.3 mycroft 198:
199: /*
200: * Fill in this entry.
201: */
202: opv_desc_vector[opve_descp->opve_op->vdesc_offset] =
203: opve_descp->opve_impl;
1.1 mycroft 204: }
1.3 mycroft 205: }
206:
1.17 jdolecek 207: static void
1.23.2.6! skrll 208: vfs_opv_init_default(const struct vnodeopv_desc *vfs_opv_desc)
1.3 mycroft 209: {
210: int j;
1.23.2.1 skrll 211: int (**opv_desc_vector)(void *);
1.3 mycroft 212:
213: opv_desc_vector = *(vfs_opv_desc->opv_desc_vector_p);
214:
215: /*
216: * Force every operations vector to have a default routine.
217: */
218: if (opv_desc_vector[VOFFSET(vop_default)] == NULL)
219: panic("vfs_opv_init: operation vector without default routine.");
220:
1.17 jdolecek 221: for (j = 0; j < VNODE_OPS_COUNT; j++)
1.3 mycroft 222: if (opv_desc_vector[j] == NULL)
1.23.2.4 skrll 223: opv_desc_vector[j] =
1.3 mycroft 224: opv_desc_vector[VOFFSET(vop_default)];
225: }
226:
227: void
1.23.2.6! skrll 228: vfs_opv_init(const struct vnodeopv_desc * const *vopvdpp)
1.3 mycroft 229: {
1.23.2.1 skrll 230: int (**opv_desc_vector)(void *);
1.3 mycroft 231: int i;
232:
233: /*
1.9 thorpej 234: * Allocate the vectors.
1.3 mycroft 235: */
1.9 thorpej 236: for (i = 0; vopvdpp[i] != NULL; i++) {
237: /* XXX - shouldn't be M_VNODE */
238: opv_desc_vector =
1.17 jdolecek 239: malloc(VNODE_OPS_COUNT * sizeof(PFI), M_VNODE, M_WAITOK);
240: memset(opv_desc_vector, 0, VNODE_OPS_COUNT * sizeof(PFI));
1.9 thorpej 241: *(vopvdpp[i]->opv_desc_vector_p) = opv_desc_vector;
242: DODEBUG(printf("vector at %p allocated\n",
243: opv_desc_vector_p));
244: }
245:
246: /*
247: * ...and fill them in.
248: */
249: for (i = 0; vopvdpp[i] != NULL; i++)
250: vfs_opv_init_explicit(vopvdpp[i]);
1.3 mycroft 251:
1.1 mycroft 252: /*
253: * Finally, go back and replace unfilled routines
1.3 mycroft 254: * with their default.
1.1 mycroft 255: */
1.9 thorpej 256: for (i = 0; vopvdpp[i] != NULL; i++)
257: vfs_opv_init_default(vopvdpp[i]);
258: }
259:
260: void
1.23.2.6! skrll 261: vfs_opv_free(const struct vnodeopv_desc * const *vopvdpp)
1.9 thorpej 262: {
263: int i;
264:
265: /*
266: * Free the vectors allocated in vfs_opv_init().
267: */
268: for (i = 0; vopvdpp[i] != NULL; i++) {
269: /* XXX - shouldn't be M_VNODE */
270: free(*(vopvdpp[i]->opv_desc_vector_p), M_VNODE);
271: *(vopvdpp[i]->opv_desc_vector_p) = NULL;
272: }
1.1 mycroft 273: }
274:
1.17 jdolecek 275: #ifdef DEBUG
276: static void
1.23.2.6! skrll 277: vfs_op_check(void)
1.1 mycroft 278: {
279: int i;
280:
1.8 christos 281: DODEBUG(printf("Vnode_interface_init.\n"));
1.17 jdolecek 282:
1.1 mycroft 283: /*
1.17 jdolecek 284: * Check offset of each op.
1.1 mycroft 285: */
1.17 jdolecek 286: for (i = 0; vfs_op_descs[i]; i++) {
287: if (vfs_op_descs[i]->vdesc_offset != i)
288: panic("vfs_op_check: vfs_op_desc[] offset mismatch");
289: }
290:
291: if (i != VNODE_OPS_COUNT) {
292: panic("vfs_op_check: vnode ops count mismatch (%d != %d)",
293: i, VNODE_OPS_COUNT);
1.1 mycroft 294: }
1.17 jdolecek 295:
296: DODEBUG(printf ("vfs_opv_numops=%d\n", VNODE_OPS_COUNT));
1.1 mycroft 297: }
1.17 jdolecek 298: #endif /* DEBUG */
1.1 mycroft 299:
300: /*
301: * Routines having to do with the management of the vnode table.
302: */
303: struct vattr va_null;
304:
305: /*
306: * Initialize the vnode structures and initialize each file system type.
307: */
1.5 christos 308: void
1.23.2.6! skrll 309: vfsinit(void)
1.1 mycroft 310: {
1.23.2.5 skrll 311: __link_set_decl(vfsops, struct vfsops);
312: struct vfsops * const *vfsp;
1.16 thorpej 313:
314: /*
1.19 thorpej 315: * Initialize the namei pathname buffer pool and cache.
1.16 thorpej 316: */
317: pool_init(&pnbuf_pool, MAXPATHLEN, 0, 0, 0, "pnbufpl",
1.21 thorpej 318: &pool_allocator_nointr);
1.19 thorpej 319: pool_cache_init(&pnbuf_cache, &pnbuf_pool, NULL, NULL, NULL);
1.1 mycroft 320:
321: /*
322: * Initialize the vnode table
323: */
324: vntblinit();
1.9 thorpej 325:
1.1 mycroft 326: /*
327: * Initialize the vnode name cache
328: */
329: nchinit();
1.9 thorpej 330:
1.17 jdolecek 331: #ifdef DEBUG
1.1 mycroft 332: /*
1.17 jdolecek 333: * Check the list of vnode operations.
1.1 mycroft 334: */
1.17 jdolecek 335: vfs_op_check();
336: #endif
1.9 thorpej 337:
1.1 mycroft 338: /*
1.9 thorpej 339: * Initialize the special vnode operations.
340: */
341: vfs_opv_init(vfs_special_vnodeopv_descs);
342:
343: /*
344: * Establish each file system which was statically
345: * included in the kernel.
1.1 mycroft 346: */
347: vattr_null(&va_null);
1.23.2.5 skrll 348: __link_set_foreach(vfsp, vfsops) {
349: if (vfs_attach(*vfsp)) {
1.9 thorpej 350: printf("multiple `%s' file systems",
1.23.2.5 skrll 351: (*vfsp)->vfs_name);
1.9 thorpej 352: panic("vfsinit");
353: }
1.1 mycroft 354: }
355: }
CVSweb <webmaster@jp.NetBSD.org>