summaryrefslogtreecommitdiff
path: root/ext
diff options
context:
space:
mode:
authornagachika <nagachika@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2015-05-23 17:15:12 +0000
committernagachika <nagachika@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2015-05-23 17:15:12 +0000
commitc92fa1fdad2e9574baddc71a006c0d2f5caea20a (patch)
tree07c6f6a77434f7153da14000ad8070f58870e6ba /ext
parent92e97984c60d4f3f43479537e1510039fec9fa28 (diff)
merge revision(s) 50071,50088: [Backport #10998] [Backport #11000]
* ext/-test-/file/fs.c (get_fsname): return filesystem name by statfs/statvfs. [ruby-core:68624] [Bug #10998] * ext/-test-/file/fs.c (get_fsname): try magic number only if f_type is included. [ruby-dev:48913] [Bug #11000] git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/branches/ruby_2_2@50621 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
Diffstat (limited to 'ext')
-rw-r--r--ext/-test-/file/extconf.rb14
-rw-r--r--ext/-test-/file/fs.c90
2 files changed, 66 insertions, 38 deletions
diff --git a/ext/-test-/file/extconf.rb b/ext/-test-/file/extconf.rb
index 4e134dd1bf..be4a2fbdeb 100644
--- a/ext/-test-/file/extconf.rb
+++ b/ext/-test-/file/extconf.rb
@@ -1,4 +1,18 @@
$INCFLAGS << " -I$(topdir) -I$(top_srcdir)"
+
+headers = %w[sys/param.h sys/mount.h sys/vfs.h].select {|h| have_header(h)}
+if have_type("struct statfs", headers)
+ have_struct_member("struct statfs", "f_fstypename", headers)
+ have_struct_member("struct statfs", "f_type", headers)
+end
+
+headers = %w[sys/statvfs.h]
+if have_type("struct statvfs", headers)
+ have_struct_member("struct statvfs", "f_fstypename", headers)
+ have_struct_member("struct statvfs", "f_basetype", headers)
+ have_struct_member("struct statvfs", "f_type", headers)
+end
+
$srcs = Dir[File.join($srcdir, "*.{#{SRC_EXT.join(%q{,})}}")]
inits = $srcs.map {|s| File.basename(s, ".*")}
inits.delete("init")
diff --git a/ext/-test-/file/fs.c b/ext/-test-/file/fs.c
index 4a41bf33b9..1ab067e1b2 100644
--- a/ext/-test-/file/fs.c
+++ b/ext/-test-/file/fs.c
@@ -1,55 +1,69 @@
#include "ruby/ruby.h"
#include "ruby/io.h"
-#ifdef __linux__
-# define HAVE_GETMNTENT
+#ifdef HAVE_SYS_MOUNT_H
+#include <sys/mount.h>
+#endif
+#ifdef HAVE_SYS_VFS_H
+#include <sys/vfs.h>
#endif
-#ifdef HAVE_GETMNTENT
-# include <stdio.h>
-# include <mntent.h>
+#if defined HAVE_STRUCT_STATFS_F_FSTYPENAME
+typedef struct statfs statfs_t;
+# define STATFS(f, s) statfs((f), (s))
+# define HAVE_STRUCT_STATFS_T_F_FSTYPENAME 1
+# if defined HAVE_STRUCT_STATFS_F_TYPE
+# define HAVE_STRUCT_STATFS_T_F_TYPE 1
+# endif
+#elif defined(HAVE_STRUCT_STATVFS_F_FSTYPENAME) /* NetBSD */
+typedef struct statvfs statfs_t;
+# define STATFS(f, s) statvfs((f), (s))
+# define HAVE_STRUCT_STATFS_T_F_FSTYPENAME 1
+# if defined HAVE_STRUCT_STATVFS_F_TYPE
+# define HAVE_STRUCT_STATFS_T_F_TYPE 1
+# endif
+#elif defined(HAVE_STRUCT_STATVFS_F_BASETYPE) /* AIX, HP-UX, Solaris */
+typedef struct statvfs statfs_t;
+# define STATFS(f, s) statvfs((f), (s))
+# define HAVE_STRUCT_STATFS_T_F_FSTYPENAME 1
+# define f_fstypename f_basetype
+# if defined HAVE_STRUCT_STATVFS_F_TYPE
+# define HAVE_STRUCT_STATFS_T_F_TYPE 1
+# endif
#endif
VALUE
get_fsname(VALUE self, VALUE str)
{
-#ifdef HAVE_GETMNTENT
- const char *path;
- struct mntent mntbuf;
- static const int buflen = 4096;
- char *buf = alloca(buflen);
- int len = 0;
- FILE *fp;
-#define FSNAME_LEN 100
- char name[FSNAME_LEN] = "";
+#ifdef STATFS
+ statfs_t st;
+# define CSTR(s) rb_str_new_cstr(s)
FilePathValue(str);
- path = RSTRING_PTR(str);
- fp = setmntent("/etc/mtab", "r");
- if (!fp) rb_sys_fail("setmntent(/etb/mtab)");;
-
- while (getmntent_r(fp, &mntbuf, buf, buflen)) {
- int i;
- char *mnt_dir = mntbuf.mnt_dir;
- for (i=0; mnt_dir[i]; i++) {
- if (mnt_dir[i] != path[i]) {
- goto next_entry;
- }
- }
- if (i >= len) {
- len = i;
- strlcpy(name, mntbuf.mnt_type, FSNAME_LEN);
- }
-next_entry:
- ;
+ str = rb_str_encode_ospath(str);
+ if (STATFS(StringValueCStr(str), &st) == -1) {
+ rb_sys_fail_str(str);
}
- endmntent(fp);
-
- if (!len) rb_sys_fail("no matching entry");;
- return rb_str_new_cstr(name);
-#else
- return Qnil;
+# ifdef HAVE_STRUCT_STATFS_T_F_FSTYPENAME
+ if (st.f_fstypename[0])
+ return CSTR(st.f_fstypename);
+# endif
+# ifdef HAVE_STRUCT_STATFS_T_F_TYPE
+ switch (st.f_type) {
+ case 0x9123683E: /* BTRFS_SUPER_MAGIC */
+ return CSTR("btrfs");
+ case 0x7461636f: /* OCFS2_SUPER_MAGIC */
+ return CSTR("ocfs");
+ case 0xEF53: /* EXT2_SUPER_MAGIC EXT3_SUPER_MAGIC EXT4_SUPER_MAGIC */
+ return CSTR("ext4");
+ case 0x58465342: /* XFS_SUPER_MAGIC */
+ return CSTR("xfs");
+ case 0x01021994: /* TMPFS_MAGIC */
+ return CSTR("tmpfs");
+ }
+# endif
#endif
+ return Qnil;
}
void