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