xref: /dflybsd-src/sys/vfs/dirfs/dirfs_vfsops.c (revision 00369c4a0b9b0df5cb692c2b5cf096f5a5a83727)
1509bc517SAntonio Huete Jimenez /*
2509bc517SAntonio Huete Jimenez  * Copyright (c) 2013 The DragonFly Project.  All rights reserved.
3509bc517SAntonio Huete Jimenez  *
4509bc517SAntonio Huete Jimenez  * This code is derived from software contributed to The DragonFly Project
5509bc517SAntonio Huete Jimenez  * by Antonio Huete Jimenez <tuxillo@quantumachine.net>
6509bc517SAntonio Huete Jimenez  * by Matthew Dillon <dillon@dragonflybsd.org>
7509bc517SAntonio Huete Jimenez  *
8509bc517SAntonio Huete Jimenez  * Redistribution and use in source and binary forms, with or without
9509bc517SAntonio Huete Jimenez  * modification, are permitted provided that the following conditions
10509bc517SAntonio Huete Jimenez  * are met:
11509bc517SAntonio Huete Jimenez  *
12509bc517SAntonio Huete Jimenez  * 1. Redistributions of source code must retain the above copyright
13509bc517SAntonio Huete Jimenez  *    notice, this list of conditions and the following disclaimer.
14509bc517SAntonio Huete Jimenez  * 2. Redistributions in binary form must reproduce the above copyright
15509bc517SAntonio Huete Jimenez  *    notice, this list of conditions and the following disclaimer in
16509bc517SAntonio Huete Jimenez  *    the documentation and/or other materials provided with the
17509bc517SAntonio Huete Jimenez  *    distribution.
18509bc517SAntonio Huete Jimenez  * 3. Neither the name of The DragonFly Project nor the names of its
19509bc517SAntonio Huete Jimenez  *    contributors may be used to endorse or promote products derived
20509bc517SAntonio Huete Jimenez  *    from this software without specific, prior written permission.
21509bc517SAntonio Huete Jimenez  *
22509bc517SAntonio Huete Jimenez  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
23509bc517SAntonio Huete Jimenez  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
24509bc517SAntonio Huete Jimenez  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
25509bc517SAntonio Huete Jimenez  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE
26509bc517SAntonio Huete Jimenez  * COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
27509bc517SAntonio Huete Jimenez  * INCIDENTAL, SPECIAL, EXEMPLARY OR CONSEQUENTIAL DAMAGES (INCLUDING,
28509bc517SAntonio Huete Jimenez  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
29509bc517SAntonio Huete Jimenez  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
30509bc517SAntonio Huete Jimenez  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
31509bc517SAntonio Huete Jimenez  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
32509bc517SAntonio Huete Jimenez  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
33509bc517SAntonio Huete Jimenez  * SUCH DAMAGE.
34509bc517SAntonio Huete Jimenez  *
35509bc517SAntonio Huete Jimenez  */
36509bc517SAntonio Huete Jimenez 
37509bc517SAntonio Huete Jimenez #include <sys/vfsops.h>
38509bc517SAntonio Huete Jimenez #include <sys/mount.h>
39509bc517SAntonio Huete Jimenez #include <sys/types.h>
40509bc517SAntonio Huete Jimenez #include <sys/systm.h>
41509bc517SAntonio Huete Jimenez #include <sys/param.h>
42509bc517SAntonio Huete Jimenez #include <sys/module.h>
43509bc517SAntonio Huete Jimenez #include <sys/kernel.h>
44509bc517SAntonio Huete Jimenez #include <sys/malloc.h>
45509bc517SAntonio Huete Jimenez #include <sys/sysctl.h>
46509bc517SAntonio Huete Jimenez #include <sys/queue.h>
47509bc517SAntonio Huete Jimenez #include <sys/spinlock2.h>
48509bc517SAntonio Huete Jimenez #include <sys/ktr.h>
49509bc517SAntonio Huete Jimenez 
50509bc517SAntonio Huete Jimenez #include <string.h>
51509bc517SAntonio Huete Jimenez 
52509bc517SAntonio Huete Jimenez #include "dirfs.h"
53509bc517SAntonio Huete Jimenez 
54509bc517SAntonio Huete Jimenez MALLOC_DEFINE(M_DIRFS, "dirfs", "dirfs mount allocation");
55509bc517SAntonio Huete Jimenez MALLOC_DEFINE(M_DIRFS_NODE, "dirfs nodes", "dirfs nodes memory allocation");
56509bc517SAntonio Huete Jimenez MALLOC_DEFINE(M_DIRFS_MISC, "dirfs misc", "dirfs miscellaneous allocation");
57509bc517SAntonio Huete Jimenez 
58509bc517SAntonio Huete Jimenez /*
59509bc517SAntonio Huete Jimenez  * Kernel tracing facilities
60509bc517SAntonio Huete Jimenez  */
61509bc517SAntonio Huete Jimenez KTR_INFO_MASTER(dirfs);
62509bc517SAntonio Huete Jimenez 
6342466a39SAntonio Huete Jimenez KTR_INFO(KTR_DIRFS, dirfs, root, 20,
64509bc517SAntonio Huete Jimenez     "DIRFS(root dnp=%p vnode=%p hostdir=%s fd=%d error=%d)",
65509bc517SAntonio Huete Jimenez     dirfs_node_t dnp, struct vnode *vp, char *hostdir, int fd, int error);
66509bc517SAntonio Huete Jimenez 
6742466a39SAntonio Huete Jimenez KTR_INFO(KTR_DIRFS, dirfs, mount, 21,
6842466a39SAntonio Huete Jimenez     "DIRFS(mount path=%s dmp=%p mp=%p error=%d)",
6942466a39SAntonio Huete Jimenez     char *path, dirfs_mount_t dmp, struct mount *mp, int error);
7042466a39SAntonio Huete Jimenez 
7142466a39SAntonio Huete Jimenez KTR_INFO(KTR_DIRFS, dirfs, unmount, 22,
7242466a39SAntonio Huete Jimenez     "DIRFS(unmount dmp=%p mp=%p error=%d)",
7342466a39SAntonio Huete Jimenez     dirfs_mount_t dmp, struct mount *mp, int error);
7442466a39SAntonio Huete Jimenez 
75509bc517SAntonio Huete Jimenez /* System wide sysctl stuff */
76f689ce95SAntonio Huete Jimenez int debuglvl = 0;
77509bc517SAntonio Huete Jimenez int dirfs_fd_limit = 100;
78509bc517SAntonio Huete Jimenez int dirfs_fd_used = 0;
79509bc517SAntonio Huete Jimenez long passive_fd_list_miss = 0;
80509bc517SAntonio Huete Jimenez long passive_fd_list_hits = 0;
81509bc517SAntonio Huete Jimenez 
82509bc517SAntonio Huete Jimenez SYSCTL_NODE(_vfs, OID_AUTO, dirfs, CTLFLAG_RW, 0,
83509bc517SAntonio Huete Jimenez     "dirfs filesystem for vkernels");
84509bc517SAntonio Huete Jimenez SYSCTL_INT(_vfs_dirfs, OID_AUTO, debug, CTLFLAG_RW,
85509bc517SAntonio Huete Jimenez     &debuglvl, 0, "dirfs debug level");
86509bc517SAntonio Huete Jimenez SYSCTL_INT(_vfs_dirfs, OID_AUTO, fd_limit, CTLFLAG_RW,
87509bc517SAntonio Huete Jimenez     &dirfs_fd_limit, 0, "Maximum number of passive nodes to cache");
88509bc517SAntonio Huete Jimenez SYSCTL_INT(_vfs_dirfs, OID_AUTO, fd_used, CTLFLAG_RD,
89509bc517SAntonio Huete Jimenez     &dirfs_fd_used, 0, "Current number of passive nodes cached");
90509bc517SAntonio Huete Jimenez SYSCTL_LONG(_vfs_dirfs, OID_AUTO, passive_fd_list_miss, CTLFLAG_RD,
91509bc517SAntonio Huete Jimenez     &passive_fd_list_miss, 0, "Passive fd list cache misses");
92509bc517SAntonio Huete Jimenez SYSCTL_LONG(_vfs_dirfs, OID_AUTO, passive_fd_list_hits, CTLFLAG_RD,
93509bc517SAntonio Huete Jimenez     &passive_fd_list_hits, 0, "Passive fd list cache misses");
94509bc517SAntonio Huete Jimenez 
95509bc517SAntonio Huete Jimenez static int dirfs_statfs(struct mount *, struct statfs *, struct ucred *);
96509bc517SAntonio Huete Jimenez 
97509bc517SAntonio Huete Jimenez static int
dirfs_mount(struct mount * mp,char * path,caddr_t data,struct ucred * cred)98509bc517SAntonio Huete Jimenez dirfs_mount(struct mount *mp, char *path, caddr_t data, struct ucred *cred)
99509bc517SAntonio Huete Jimenez {
100509bc517SAntonio Huete Jimenez 	dirfs_mount_t dmp;
101509bc517SAntonio Huete Jimenez 	struct stat st;
102509bc517SAntonio Huete Jimenez 	size_t done, nlen;
103509bc517SAntonio Huete Jimenez 	int error;
104509bc517SAntonio Huete Jimenez 
10526ec059cSAntonio Huete Jimenez 	dbg(1, "called\n");
106509bc517SAntonio Huete Jimenez 
107509bc517SAntonio Huete Jimenez 	if (mp->mnt_flag & MNT_UPDATE) {
108509bc517SAntonio Huete Jimenez 		dmp = VFS_TO_DIRFS(mp);
109509bc517SAntonio Huete Jimenez 		if (dmp->dm_rdonly == 0 && (mp->mnt_flag & MNT_RDONLY)) {
110509bc517SAntonio Huete Jimenez 			/* XXX We should make sure all writes are synced */
111509bc517SAntonio Huete Jimenez 			dmp->dm_rdonly = 1;
112509bc517SAntonio Huete Jimenez 			debug(2, "dirfs read-write -> read-only\n");
113509bc517SAntonio Huete Jimenez 		}
114509bc517SAntonio Huete Jimenez 
115509bc517SAntonio Huete Jimenez 		if (dmp->dm_rdonly && (mp->mnt_kern_flag & MNTK_WANTRDWR)) {
116509bc517SAntonio Huete Jimenez 			debug(2, "dirfs read-only -> read-write\n");
117509bc517SAntonio Huete Jimenez 			dmp->dm_rdonly = 0;
118509bc517SAntonio Huete Jimenez 		}
119509bc517SAntonio Huete Jimenez 		return 0;
120509bc517SAntonio Huete Jimenez 	}
121509bc517SAntonio Huete Jimenez 
122509bc517SAntonio Huete Jimenez 	dmp = kmalloc(sizeof(*dmp), M_DIRFS, M_WAITOK | M_ZERO);
123509bc517SAntonio Huete Jimenez 	mp->mnt_data = (qaddr_t)dmp;
124509bc517SAntonio Huete Jimenez 	dmp->dm_mount = mp;
125509bc517SAntonio Huete Jimenez 
126509bc517SAntonio Huete Jimenez 	error = copyinstr(data, &dmp->dm_path, MAXPATHLEN, &done);
127509bc517SAntonio Huete Jimenez 	if (error) {
128509bc517SAntonio Huete Jimenez 		/* Attempt to copy from kernel address */
129509bc517SAntonio Huete Jimenez 		error = copystr(data, &dmp->dm_path, MAXPATHLEN, &done);
130509bc517SAntonio Huete Jimenez 		if (error) {
131509bc517SAntonio Huete Jimenez 			kfree(dmp, M_DIRFS);
13242466a39SAntonio Huete Jimenez 			goto failure;
133509bc517SAntonio Huete Jimenez 		}
134509bc517SAntonio Huete Jimenez 	}
135509bc517SAntonio Huete Jimenez 
136509bc517SAntonio Huete Jimenez 	/* Strip / character at the end to avoid problems */
137509bc517SAntonio Huete Jimenez 	nlen = strnlen(dmp->dm_path, MAXPATHLEN);
138509bc517SAntonio Huete Jimenez 	if (dmp->dm_path[nlen-1] == '/')
139509bc517SAntonio Huete Jimenez 		dmp->dm_path[nlen-1] = 0;
140509bc517SAntonio Huete Jimenez 
141509bc517SAntonio Huete Jimenez 	/* Make sure host directory exists and it is indeed a directory. */
142509bc517SAntonio Huete Jimenez 	if ((stat(dmp->dm_path, &st)) == 0) {
143509bc517SAntonio Huete Jimenez 		if (!S_ISDIR(st.st_mode)) {
144509bc517SAntonio Huete Jimenez 			kfree(dmp, M_DIRFS);
14542466a39SAntonio Huete Jimenez 			error = EINVAL;
14642466a39SAntonio Huete Jimenez 			goto failure;
147509bc517SAntonio Huete Jimenez 		}
148509bc517SAntonio Huete Jimenez 	} else {
14942466a39SAntonio Huete Jimenez 		error = errno;
15042466a39SAntonio Huete Jimenez 		goto failure;
151509bc517SAntonio Huete Jimenez 	}
152509bc517SAntonio Huete Jimenez 
153509bc517SAntonio Huete Jimenez 	lockinit(&dmp->dm_lock, "dfsmnt", 0, LK_CANRECURSE);
154509bc517SAntonio Huete Jimenez 
155509bc517SAntonio Huete Jimenez 	vfs_add_vnodeops(mp, &dirfs_vnode_vops, &mp->mnt_vn_norm_ops);
156509bc517SAntonio Huete Jimenez 	vfs_getnewfsid(mp);
157509bc517SAntonio Huete Jimenez 
15883837cefSAntonio Huete Jimenez 	/* Who is running the vkernel */
15983837cefSAntonio Huete Jimenez 	dmp->dm_uid = getuid();
16083837cefSAntonio Huete Jimenez 	dmp->dm_gid = getgid();
16183837cefSAntonio Huete Jimenez 
162509bc517SAntonio Huete Jimenez 	TAILQ_INIT(&dmp->dm_fdlist);
163509bc517SAntonio Huete Jimenez 	RB_INIT(&dmp->dm_inotree);
164509bc517SAntonio Huete Jimenez 
165509bc517SAntonio Huete Jimenez 	kmalloc_raise_limit(M_DIRFS_NODE, 0);
166509bc517SAntonio Huete Jimenez 
167509bc517SAntonio Huete Jimenez 	dirfs_statfs(mp, &mp->mnt_stat, cred);
168509bc517SAntonio Huete Jimenez 
16942466a39SAntonio Huete Jimenez failure:
17042466a39SAntonio Huete Jimenez 	KTR_LOG(dirfs_mount, (dmp->dm_path) ? dmp->dm_path : "NULL",
17142466a39SAntonio Huete Jimenez 	    dmp, mp, error);
172509bc517SAntonio Huete Jimenez 
17342466a39SAntonio Huete Jimenez 	return error;
174509bc517SAntonio Huete Jimenez }
175509bc517SAntonio Huete Jimenez 
176509bc517SAntonio Huete Jimenez static int
dirfs_unmount(struct mount * mp,int mntflags)177509bc517SAntonio Huete Jimenez dirfs_unmount(struct mount *mp, int mntflags)
178509bc517SAntonio Huete Jimenez {
179509bc517SAntonio Huete Jimenez 	dirfs_mount_t dmp;
180509bc517SAntonio Huete Jimenez 	dirfs_node_t dnp;
181509bc517SAntonio Huete Jimenez 	int cnt;
182509bc517SAntonio Huete Jimenez 	int error;
183509bc517SAntonio Huete Jimenez 
18426ec059cSAntonio Huete Jimenez 	dbg(1, "called\n");
185509bc517SAntonio Huete Jimenez 	cnt = 0;
186509bc517SAntonio Huete Jimenez 	dmp = VFS_TO_DIRFS(mp);
187509bc517SAntonio Huete Jimenez 
188509bc517SAntonio Huete Jimenez 	error = vflush(mp, 0, 0);
189509bc517SAntonio Huete Jimenez 	if (error)
19042466a39SAntonio Huete Jimenez 		goto failure;
191509bc517SAntonio Huete Jimenez 
192509bc517SAntonio Huete Jimenez 	/*
193509bc517SAntonio Huete Jimenez 	 * Clean up dm_fdlist.  There should be no vnodes left so the
194509bc517SAntonio Huete Jimenez 	 * only ref should be from the fdlist.
195509bc517SAntonio Huete Jimenez 	 */
196509bc517SAntonio Huete Jimenez 	while ((dnp = TAILQ_FIRST(&dmp->dm_fdlist)) != NULL) {
197509bc517SAntonio Huete Jimenez 		dirfs_node_setpassive(dmp, dnp, 0);
198509bc517SAntonio Huete Jimenez 	}
199509bc517SAntonio Huete Jimenez 
200509bc517SAntonio Huete Jimenez 	/*
20107f9fa35SAntonio Huete Jimenez 	 * Cleanup root node. In the case the filesystem is mounted
20207f9fa35SAntonio Huete Jimenez 	 * but no operation is done on it, there will be no call to
20307f9fa35SAntonio Huete Jimenez 	 * VFS_ROOT() so better check dnp is not NULL before attempting
20407f9fa35SAntonio Huete Jimenez 	 * to release it.
205509bc517SAntonio Huete Jimenez 	 */
206509bc517SAntonio Huete Jimenez 	dnp = dmp->dm_root;
20707f9fa35SAntonio Huete Jimenez 	if (dnp != NULL) {
208509bc517SAntonio Huete Jimenez 		dirfs_close_helper(dnp);
209509bc517SAntonio Huete Jimenez 		debug_node2(dnp);
210509bc517SAntonio Huete Jimenez 		dirfs_node_drop(dmp, dnp); /* last ref should free structure */
21107f9fa35SAntonio Huete Jimenez 	}
212509bc517SAntonio Huete Jimenez 	kfree(dmp, M_DIRFS);
213509bc517SAntonio Huete Jimenez 	mp->mnt_data = (qaddr_t) 0;
214509bc517SAntonio Huete Jimenez 
21542466a39SAntonio Huete Jimenez failure:
21642466a39SAntonio Huete Jimenez 	KTR_LOG(dirfs_unmount, dmp, mp, error);
217509bc517SAntonio Huete Jimenez 
21842466a39SAntonio Huete Jimenez 	return error;
219509bc517SAntonio Huete Jimenez }
220509bc517SAntonio Huete Jimenez 
221509bc517SAntonio Huete Jimenez static int
dirfs_root(struct mount * mp,struct vnode ** vpp)222509bc517SAntonio Huete Jimenez dirfs_root(struct mount *mp, struct vnode **vpp)
223509bc517SAntonio Huete Jimenez {
224509bc517SAntonio Huete Jimenez 	dirfs_mount_t dmp;
225509bc517SAntonio Huete Jimenez 	dirfs_node_t dnp;
226509bc517SAntonio Huete Jimenez 	int fd;
227509bc517SAntonio Huete Jimenez 	int error;
228509bc517SAntonio Huete Jimenez 
22926ec059cSAntonio Huete Jimenez 	dbg(1, "called\n");
230509bc517SAntonio Huete Jimenez 
231509bc517SAntonio Huete Jimenez 	dmp = VFS_TO_DIRFS(mp);
232509bc517SAntonio Huete Jimenez 	KKASSERT(dmp != NULL);
233509bc517SAntonio Huete Jimenez 
234509bc517SAntonio Huete Jimenez 	if (dmp->dm_root == NULL) {
235509bc517SAntonio Huete Jimenez 		/*
236509bc517SAntonio Huete Jimenez 		 * dm_root holds the root dirfs node. Allocate a new one since
237509bc517SAntonio Huete Jimenez 		 * there is none. Also attempt to lstat(2) it, in order to set
238509bc517SAntonio Huete Jimenez 		 * data for VOP_ACCESS()
239509bc517SAntonio Huete Jimenez 		 */
240509bc517SAntonio Huete Jimenez 		dnp = dirfs_node_alloc(mp);
241509bc517SAntonio Huete Jimenez 		error = dirfs_node_stat(DIRFS_NOFD, dmp->dm_path, dnp);
242509bc517SAntonio Huete Jimenez 		if (error != 0) {
243509bc517SAntonio Huete Jimenez 			dirfs_node_free(dmp, dnp);
244509bc517SAntonio Huete Jimenez 			return error;
245509bc517SAntonio Huete Jimenez 		}
246509bc517SAntonio Huete Jimenez 		dirfs_node_ref(dnp);	/* leave inact for life of mount */
247509bc517SAntonio Huete Jimenez 
248509bc517SAntonio Huete Jimenez 		/* Root inode's parent is NULL, used for verification */
249509bc517SAntonio Huete Jimenez 		dnp->dn_parent = NULL;
250509bc517SAntonio Huete Jimenez 		dmp->dm_root = dnp;
251509bc517SAntonio Huete Jimenez 		dirfs_node_setflags(dnp, DIRFS_ROOT);
252509bc517SAntonio Huete Jimenez 
253509bc517SAntonio Huete Jimenez 		/*
254509bc517SAntonio Huete Jimenez 		 * Maintain an open descriptor on the root dnp.  The
255509bc517SAntonio Huete Jimenez 		 * normal open/close/cache does not apply for the root
256509bc517SAntonio Huete Jimenez 		 * so the descriptor is ALWAYS available.
257509bc517SAntonio Huete Jimenez 		 */
258509bc517SAntonio Huete Jimenez 		fd = open(dmp->dm_path, O_DIRECTORY);
259509bc517SAntonio Huete Jimenez 		if (fd == -1) {
26026ec059cSAntonio Huete Jimenez 			dbg(9, "failed to open ROOT node\n");
261509bc517SAntonio Huete Jimenez 			dirfs_free_vp(dmp, dnp);
262509bc517SAntonio Huete Jimenez 			dirfs_node_free(dmp, dnp);
263509bc517SAntonio Huete Jimenez 			return errno;
264509bc517SAntonio Huete Jimenez 		}
265509bc517SAntonio Huete Jimenez 		dnp->dn_fd = fd;
266509bc517SAntonio Huete Jimenez 		dnp->dn_type = VDIR;
267509bc517SAntonio Huete Jimenez 	} else {
268509bc517SAntonio Huete Jimenez 		dnp = dmp->dm_root;
269509bc517SAntonio Huete Jimenez 	}
270509bc517SAntonio Huete Jimenez 
271509bc517SAntonio Huete Jimenez 	/*
272509bc517SAntonio Huete Jimenez 	 * Acquire the root vnode (dn_type already set above).  This
273509bc517SAntonio Huete Jimenez 	 * call will handle any races and return a locked vnode.
274509bc517SAntonio Huete Jimenez 	 */
275509bc517SAntonio Huete Jimenez 	dirfs_alloc_vp(mp, vpp, LK_CANRECURSE, dnp);
276509bc517SAntonio Huete Jimenez 	KTR_LOG(dirfs_root, dnp, *vpp, dmp->dm_path, dnp->dn_fd, error);
277509bc517SAntonio Huete Jimenez 
278509bc517SAntonio Huete Jimenez 	return 0;
279509bc517SAntonio Huete Jimenez }
280509bc517SAntonio Huete Jimenez 
281509bc517SAntonio Huete Jimenez static int
dirfs_fhtovp(struct mount * mp,struct vnode * rootvp,struct fid * fhp,struct vnode ** vpp)282509bc517SAntonio Huete Jimenez dirfs_fhtovp(struct mount *mp, struct vnode *rootvp, struct fid *fhp, struct vnode **vpp)
283509bc517SAntonio Huete Jimenez {
28426ec059cSAntonio Huete Jimenez 	dbg(1, "called\n");
285509bc517SAntonio Huete Jimenez 
286509bc517SAntonio Huete Jimenez 	return EOPNOTSUPP;
287509bc517SAntonio Huete Jimenez }
288509bc517SAntonio Huete Jimenez 
289509bc517SAntonio Huete Jimenez static int
dirfs_statfs(struct mount * mp,struct statfs * sbp,struct ucred * cred)290509bc517SAntonio Huete Jimenez dirfs_statfs(struct mount *mp, struct statfs *sbp, struct ucred *cred)
291509bc517SAntonio Huete Jimenez {
292509bc517SAntonio Huete Jimenez 	dirfs_mount_t dmp = VFS_TO_DIRFS(mp);
293509bc517SAntonio Huete Jimenez 	struct statfs st;
294509bc517SAntonio Huete Jimenez 
29526ec059cSAntonio Huete Jimenez 	dbg(1, "called\n");
296509bc517SAntonio Huete Jimenez 
297509bc517SAntonio Huete Jimenez 	if((statfs(dmp->dm_path, &st)) == -1)
298509bc517SAntonio Huete Jimenez 		return errno;
299509bc517SAntonio Huete Jimenez 
300509bc517SAntonio Huete Jimenez 	ksnprintf(st.f_mntfromname, MNAMELEN - 1, "dirfs@%s", dmp->dm_path);
301509bc517SAntonio Huete Jimenez 	bcopy(&st, sbp, sizeof(st));
302509bc517SAntonio Huete Jimenez 	strlcpy(sbp->f_fstypename, mp->mnt_vfc->vfc_name, MFSNAMELEN);
303509bc517SAntonio Huete Jimenez 	dbg(5, "iosize = %zd\n", sbp->f_iosize);
304509bc517SAntonio Huete Jimenez 
305509bc517SAntonio Huete Jimenez 	return 0;
306509bc517SAntonio Huete Jimenez }
307509bc517SAntonio Huete Jimenez 
308509bc517SAntonio Huete Jimenez static int
dirfs_statvfs(struct mount * mp,struct statvfs * sbp,struct ucred * cred)30934a96eb9SAntonio Huete Jimenez dirfs_statvfs(struct mount *mp, struct statvfs *sbp, struct ucred *cred)
31034a96eb9SAntonio Huete Jimenez {
31134a96eb9SAntonio Huete Jimenez 	dirfs_mount_t dmp = VFS_TO_DIRFS(mp);
31234a96eb9SAntonio Huete Jimenez 	struct statvfs st;
31334a96eb9SAntonio Huete Jimenez 
31426ec059cSAntonio Huete Jimenez 	dbg(1, "called\n");
31534a96eb9SAntonio Huete Jimenez 
31634a96eb9SAntonio Huete Jimenez 	if ((statvfs(dmp->dm_path, &st)) == -1)
31734a96eb9SAntonio Huete Jimenez 		return errno;
31834a96eb9SAntonio Huete Jimenez 
31934a96eb9SAntonio Huete Jimenez 	bcopy(&st, sbp, sizeof(st));
32034a96eb9SAntonio Huete Jimenez 
32134a96eb9SAntonio Huete Jimenez 	return 0;
32234a96eb9SAntonio Huete Jimenez }
32334a96eb9SAntonio Huete Jimenez 
32434a96eb9SAntonio Huete Jimenez static int
dirfs_vptofh(struct vnode * vp,struct fid * fhp)325509bc517SAntonio Huete Jimenez dirfs_vptofh(struct vnode *vp, struct fid *fhp)
326509bc517SAntonio Huete Jimenez {
327509bc517SAntonio Huete Jimenez 	dirfs_node_t dnp;
328509bc517SAntonio Huete Jimenez 
329509bc517SAntonio Huete Jimenez 	dnp = VP_TO_NODE(vp);
330509bc517SAntonio Huete Jimenez 	debug_node2(dnp);
33126ec059cSAntonio Huete Jimenez 	dbg(1, "called\n");
332509bc517SAntonio Huete Jimenez 
333509bc517SAntonio Huete Jimenez 	return EOPNOTSUPP;
334509bc517SAntonio Huete Jimenez }
335509bc517SAntonio Huete Jimenez 
336509bc517SAntonio Huete Jimenez static int
dirfs_checkexp(struct mount * mp,struct sockaddr * nam,int * exflagsp,struct ucred ** credanonp)337509bc517SAntonio Huete Jimenez dirfs_checkexp(struct mount *mp, struct sockaddr *nam, int *exflagsp,
338509bc517SAntonio Huete Jimenez 	       struct ucred **credanonp)
339509bc517SAntonio Huete Jimenez {
34026ec059cSAntonio Huete Jimenez 	dbg(1, "called\n");
341509bc517SAntonio Huete Jimenez 
342509bc517SAntonio Huete Jimenez 	return EOPNOTSUPP;
343509bc517SAntonio Huete Jimenez }
344509bc517SAntonio Huete Jimenez 
345509bc517SAntonio Huete Jimenez static struct vfsops dirfs_vfsops = {
346*00369c4aSMatthew Dillon 	.vfs_flags =			0,
347509bc517SAntonio Huete Jimenez 	.vfs_mount =			dirfs_mount,
348509bc517SAntonio Huete Jimenez 	.vfs_unmount =			dirfs_unmount,
349509bc517SAntonio Huete Jimenez 	.vfs_root =			dirfs_root,
350509bc517SAntonio Huete Jimenez 	.vfs_vget =			vfs_stdvget,
351509bc517SAntonio Huete Jimenez 	.vfs_statfs =			dirfs_statfs,
35234a96eb9SAntonio Huete Jimenez 	.vfs_statvfs =			dirfs_statvfs,
353509bc517SAntonio Huete Jimenez 	.vfs_fhtovp =			dirfs_fhtovp,
354509bc517SAntonio Huete Jimenez 	.vfs_vptofh =			dirfs_vptofh,
355509bc517SAntonio Huete Jimenez 	.vfs_checkexp =			dirfs_checkexp
356509bc517SAntonio Huete Jimenez };
357509bc517SAntonio Huete Jimenez 
358509bc517SAntonio Huete Jimenez VFS_SET(dirfs_vfsops, dirfs, 0);
359509bc517SAntonio Huete Jimenez MODULE_VERSION(dirfs, 1);
360