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