xref: /dragonfly/lib/libc/gen/getvfsent.c (revision e5a92d33)
1 /*
2  * getvfsent.c - get a listing of installed filesystems
3  * Written September 1994 by Garrett A. Wollman
4  * This file is in the public domain.
5  *
6  * $FreeBSD: src/lib/libc/gen/getvfsent.c,v 1.14.2.1 2001/03/05 09:19:38 obrien Exp $
7  */
8 
9 #include <sys/param.h>
10 #include <sys/linker.h>
11 #include <sys/mount.h>
12 #include <sys/sysctl.h>
13 #include <stdlib.h>
14 #include <string.h>
15 #include <unistd.h>
16 
17 /* XXX hide some compatibility problems. */
18 #undef getvfsbyname
19 
20 static struct ovfsconf *_vfslist = NULL;
21 static struct ovfsconf _vfsconf;
22 static size_t _vfslistlen = 0;
23 static int _vfs_keeplist = 0;
24 static size_t _vfs_index = 0;
25 
26 static int
27 initvfs(void)
28 {
29 	int mib[2] = { CTL_VFS, VFS_VFSCONF };
30 	size_t size = 0;
31 	int rv;
32 
33 	rv = sysctl(mib, 2, NULL, &size, NULL, (size_t)0);
34 	if(rv < 0)
35 		return 0;
36 
37 	if(_vfslist)
38 		free(_vfslist);
39 	_vfslist = malloc(size);
40 	if(!_vfslist)
41 		return 0;
42 
43 	rv = sysctl(mib, 2, _vfslist, &size, NULL, (size_t)0);
44 	if(rv < 0) {
45 		free(_vfslist);
46 		_vfslist = NULL;
47 		return 0;
48 	}
49 
50 	_vfslistlen = size / sizeof(_vfslist[0]);
51 	return 1;
52 }
53 
54 struct ovfsconf *
55 getvfsent(void)
56 {
57 	if(!_vfslist && !initvfs())
58 		return 0;
59 
60 	do {
61 		if(_vfs_index >= _vfslistlen)
62 			return 0;
63 
64 		_vfsconf = _vfslist[_vfs_index++];
65 	} while(!_vfsconf.vfc_vfsops);
66 
67 	if(!_vfs_keeplist) {
68 		free(_vfslist);
69 		_vfslist = NULL;
70 	}
71 	return &_vfsconf;
72 }
73 
74 struct ovfsconf *
75 getvfsbyname(const char *name)
76 {
77 	size_t i;
78 
79 	if(!_vfslist && !initvfs())
80 		return 0;
81 
82 	for(i = 0; i < _vfslistlen; i++) {
83 		if( ! strcmp(_vfslist[i].vfc_name, name) )
84 			break;
85 	}
86 
87 	if(i < _vfslistlen)
88 		_vfsconf = _vfslist[i];
89 
90 	if(!_vfs_keeplist) {
91 		free(_vfslist);
92 		_vfslist = NULL;
93 	}
94 
95 	if(i < _vfslistlen)
96 		return &_vfsconf;
97 	else
98 		return 0;
99 }
100 
101 struct ovfsconf *
102 getvfsbytype(int type)
103 {
104 	size_t i;
105 
106 	if(!_vfslist && !initvfs())
107 		return 0;
108 
109 	for(i = 0; i < _vfslistlen; i++) {
110 		if(_vfslist[i].vfc_index == type)
111 			break;
112 	}
113 
114 	if(i < _vfslistlen)
115 		_vfsconf = _vfslist[i];
116 
117 	if(!_vfs_keeplist) {
118 		free(_vfslist);
119 		_vfslist = NULL;
120 	}
121 
122 	if(i < _vfslistlen)
123 		return &_vfsconf;
124 	else
125 		return 0;
126 }
127 
128 void
129 setvfsent(int keep)
130 {
131 	if(_vfslist && !keep) {
132 		free(_vfslist);
133 		_vfslist = NULL;
134 	}
135 
136 	_vfs_keeplist = keep;
137 	_vfs_index = 0;
138 }
139 
140 void
141 endvfsent(void)
142 {
143 	if(_vfslist) {
144 		free(_vfslist);
145 		_vfslist = NULL;
146 	}
147 
148 	_vfs_index = 0;
149 }
150 
151 int
152 vfsisloadable(const char *name __unused)
153 {
154 	return 1;
155 }
156 
157 int
158 vfsload(const char *name)
159 {
160 	int status;
161 
162 	status = kldload(name);
163 	return status == -1 ? status : 0;
164 }
165