1 /* fstype.c -- determine type of filesystems that files are on
2 Copyright (C) 1990, 91, 92, 93, 94, 2000, 2004 Free Software Foundation, Inc.
4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation; either version 2, or (at your option)
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
14 You should have received a copy of the GNU General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
20 /* Written by David MacKenzie <djm@gnu.org>.
22 * Converted to use gnulib's read_file_system_list()
23 * by James Youngman <jay@gnu.org> (which saves a lot
24 * of manual hacking of configure.in).
33 #ifdef HAVE_SYS_TYPES_H
34 #include <sys/types.h>
41 #ifdef HAVE_SYS_MNTIO_H
45 #include <sys/mntio.h>
47 #ifdef HAVE_SYS_MKDEV_H
48 #include <sys/mkdev.h>
58 #include "../gnulib/lib/dirname.h"
62 /* Need declaration of function `xstrtoumax' */
63 #include "../gnulib/lib/xstrtol.h"
65 #include "extendbuf.h"
66 #include "mountlist.h"
72 # define _(Text) gettext (Text)
77 # define N_(String) gettext_noop (String)
79 /* See locate.c for explanation as to why not use (String) */
80 # define N_(String) String
83 static char *filesystem_type_uncached
PARAMS((const struct stat
*statp
));
86 /* Get MNTTYPE_IGNORE if it is available. */
92 # include <sys/mnttab.h>
100 free_file_system_list(struct mount_entry
*p
)
104 struct mount_entry
*pnext
= p
->me_next
;
107 free(p
->me_mountdir
);
109 if(p
->me_type_malloced
)
121 #include <netinet/in.h>
122 #include <afs/venus.h>
124 /* On SunOS 4, afs/vice.h defines this to rely on a pre-ANSI cpp. */
126 #define _VICEIOCTL(id) ((unsigned int ) _IOW('V', id, struct ViceIoctl))
129 /* AFS on Solaris 2.3 doesn't get this definition. */
130 #include <sys/ioccom.h>
136 static char space
[2048];
140 vi
.out_size
= sizeof (space
);
143 if (pioctl (path
, VIOC_FILE_CELL_NAME
, &vi
, 1)
144 && (errno
== EINVAL
|| errno
== ENOENT
))
150 /* Nonzero if the current filesystem's type is known. */
151 static int fstype_known
= 0;
153 /* Return a static string naming the type of filesystem that the file PATH,
154 described by STATP, is on.
155 RELPATH is the file name relative to the current directory.
156 Return "unknown" if its filesystem type is unknown. */
159 filesystem_type (const struct stat
*statp
)
161 static char *current_fstype
= NULL
;
162 static dev_t current_dev
;
164 if (current_fstype
!= NULL
)
166 if (fstype_known
&& statp
->st_dev
== current_dev
)
167 return current_fstype
; /* Cached value. */
168 free (current_fstype
);
170 current_dev
= statp
->st_dev
;
171 current_fstype
= filesystem_type_uncached (statp
);
172 return current_fstype
;
176 set_fstype_devno(struct mount_entry
*p
)
180 if (p
->me_dev
== (dev_t
)-1)
182 if (0 == (options
.xstat
)(p
->me_mountdir
, &stbuf
))
184 p
->me_dev
= stbuf
.st_dev
;
192 return 0; /* not needed */
196 /* Return a newly allocated string naming the type of filesystem that the
197 file PATH, described by STATP, is on.
198 RELPATH is the file name relative to the current directory.
199 Return "unknown" if its filesystem type is unknown. */
202 filesystem_type_uncached (const struct stat
*statp
)
204 struct mount_entry
*entries
, *entry
;
211 return xstrdup("afs");
215 entries
= read_file_system_list(true);
216 for (type
=NULL
, entry
=entries
; entry
; entry
=entry
->me_next
)
218 #ifdef MNTTYPE_IGNORE
219 if (!strcmp (entry
->me_type
, MNTTYPE_IGNORE
))
222 set_fstype_devno(entry
);
223 if (entry
->me_dev
== statp
->st_dev
)
224 type
= xstrdup(entry
->me_type
);
226 free_file_system_list(entries
);
228 /* Don't cache unknown values. */
229 fstype_known
= (type
!= NULL
);
231 return type
? type
: xstrdup(_("unknown"));
236 get_mounted_filesystems (void)
239 size_t alloc_size
= 0u;
241 struct mount_entry
*entries
, *entry
;
243 entries
= read_file_system_list(false);
244 for (entry
=entries
; entry
; entry
=entry
->me_next
)
248 #ifdef MNTTYPE_IGNORE
249 if (!strcmp (entry
->me_type
, MNTTYPE_IGNORE
))
252 set_fstype_devno(entry
);
254 len
= strlen(entry
->me_mountdir
) + 1;
255 result
= extendbuf(result
, used
+len
, &alloc_size
);
256 strcpy(&result
[used
], entry
->me_mountdir
);
257 used
+= len
; /* len already includes one for the \0 */
260 free_file_system_list(entries
);
266 get_mounted_devices (size_t *n
)
268 size_t alloc_size
= 0u;
270 struct mount_entry
*entries
, *entry
;
271 dev_t
*result
= NULL
;
273 for (entry
= entries
= read_file_system_list(false);
275 entry
= entry
->me_next
)
277 result
= extendbuf(result
, sizeof(dev_t
)*(used
+1), &alloc_size
);
278 set_fstype_devno(entry
);
279 result
[used
] = entry
->me_dev
;
282 free_file_system_list(entries
);