glocalfile: Do not call statfs/statvfs several times

statfs/statvfs is called several times when querying filesystem info.
This is because the G_FILE_ATTRIBUTE_FILESYSTEM_REMOTE attribute is set
over is_remote_fs function, which calls statfs/statvfs again. Let's use
the already known fstype instead of redundant statfs/statvfs calls.
This also changes g_local_file_is_remote implementation to use
g_local_file_query_filesystem_info to obtain fstype, which allows to
remove duplicated code from is_remote_fs function.
This commit is contained in:
Ondrej Holy 2020-06-15 17:24:37 +02:00
parent 706dc6b5aa
commit f489f6c4ee

View File

@ -113,7 +113,7 @@ G_DEFINE_TYPE_WITH_CODE (GLocalFile, g_local_file, G_TYPE_OBJECT,
static char *find_mountpoint_for (const char *file, dev_t dev, gboolean resolve_basename_symlink); static char *find_mountpoint_for (const char *file, dev_t dev, gboolean resolve_basename_symlink);
#ifndef G_OS_WIN32 #ifndef G_OS_WIN32
static gboolean is_remote_fs (const gchar *filename); static gboolean is_remote_fs_type (const gchar *fsname);
#endif #endif
static void static void
@ -1120,7 +1120,7 @@ g_local_file_query_filesystem_info (GFile *file,
if (g_file_attribute_matcher_matches (attribute_matcher, if (g_file_attribute_matcher_matches (attribute_matcher,
G_FILE_ATTRIBUTE_FILESYSTEM_REMOTE)) G_FILE_ATTRIBUTE_FILESYSTEM_REMOTE))
g_file_info_set_attribute_boolean (info, G_FILE_ATTRIBUTE_FILESYSTEM_REMOTE, g_file_info_set_attribute_boolean (info, G_FILE_ATTRIBUTE_FILESYSTEM_REMOTE,
is_remote_fs (local->filename)); is_remote_fs_type (fstype));
#endif #endif
g_file_attribute_matcher_unref (attribute_matcher); g_file_attribute_matcher_unref (attribute_matcher);
@ -2524,43 +2524,8 @@ g_local_file_is_remote (const gchar *filename)
#else #else
static gboolean static gboolean
is_remote_fs (const gchar *filename) is_remote_fs_type (const gchar *fsname)
{ {
const char *fsname = NULL;
#ifdef USE_STATFS
struct statfs statfs_buffer;
int statfs_result = 0;
#if STATFS_ARGS == 2
statfs_result = statfs (filename, &statfs_buffer);
#elif STATFS_ARGS == 4
statfs_result = statfs (filename, &statfs_buffer, sizeof (statfs_buffer), 0);
#endif
#elif defined(USE_STATVFS)
struct statvfs statfs_buffer;
int statfs_result = 0;
statfs_result = statvfs (filename, &statfs_buffer);
#else
return FALSE;
#endif
if (statfs_result == -1)
return FALSE;
#ifdef USE_STATFS
#if defined(HAVE_STRUCT_STATFS_F_FSTYPENAME)
fsname = statfs_buffer.f_fstypename;
#else
fsname = get_fs_type (statfs_buffer.f_type);
#endif
#elif defined(USE_STATVFS) && defined(HAVE_STRUCT_STATVFS_F_BASETYPE)
fsname = statfs_buffer.f_basetype;
#endif
if (fsname != NULL) if (fsname != NULL)
{ {
if (strcmp (fsname, "nfs") == 0) if (strcmp (fsname, "nfs") == 0)
@ -2584,7 +2549,18 @@ g_local_file_is_remote (const gchar *filename)
{ {
if (g_once_init_enter (&initialized)) if (g_once_init_enter (&initialized))
{ {
remote_home = is_remote_fs (home); GFile *file;
GFileInfo *info;
const gchar *fs_type = NULL;
file = _g_local_file_new (home);
info = g_local_file_query_filesystem_info (file, G_FILE_ATTRIBUTE_FILESYSTEM_TYPE, NULL, NULL);
if (info != NULL)
fs_type = g_file_info_get_attribute_string (info, G_FILE_ATTRIBUTE_FILESYSTEM_TYPE);
remote_home = is_remote_fs_type (fs_type);
g_clear_object (&info);
g_object_unref (file);
g_once_init_leave (&initialized, TRUE); g_once_init_leave (&initialized, TRUE);
} }
return remote_home; return remote_home;