From: Jiri Denemark <jdenemar(a)redhat.com>
The code from virFileIsSharedFSType which finds the longest existing
path for a given input is separated into a new helper so that it can be
reused elsewhere.
Signed-off-by: Jiri Denemark <jdenemar(a)redhat.com>
---
Notes:
If you wonder why the code is almost the same as the original one, but
not exactly the same, it's because I rewrote the code using stat(), but
than realized that mocking it for our tests would be a nightmare. So I
replaced stat() with statfs() :-)
src/util/virfile.c | 60 ++++++++++++++++++++++++----------------------
1 file changed, 31 insertions(+), 29 deletions(-)
diff --git a/src/util/virfile.c b/src/util/virfile.c
index 242aa7ff88..ef1bc0bbf3 100644
--- a/src/util/virfile.c
+++ b/src/util/virfile.c
@@ -3557,6 +3557,34 @@ virFileIsSharedFsFUSE(const char *path,
}
+static char *
+virFileGetExistingParent(const char *path)
+{
+ g_autofree char *dirpath = g_strdup(path);
+ struct statfs sb;
+ char *p = NULL;
+
+ /* Try less and less of the path until we get to a directory we can stat.
+ * Even if we don't have 'x' permission on any directory in the path on
the
+ * NFS server (assuming it's NFS), we will be able to stat the mount point.
+ */
+ while (statfs(dirpath, &sb) < 0 && p != dirpath) {
+ if (!(p = strrchr(dirpath, '/'))) {
+ virReportSystemError(EINVAL,
+ _("Invalid relative path '%1$s'"),
path);
+ return NULL;
+ }
+
+ if (p == dirpath)
+ *(p + 1) = '\0';
+ else
+ *p = '\0';
+ }
+
+ return g_steal_pointer(&dirpath);
+}
+
+
static const struct virFileSharedFsData virFileSharedFs[] = {
{ .fstype = VIR_FILE_SHFS_NFS, .magic = NFS_SUPER_MAGIC },
{ .fstype = VIR_FILE_SHFS_GFS2, .magic = GFS2_MAGIC },
@@ -3576,40 +3604,14 @@ virFileIsSharedFSType(const char *path,
unsigned int fstypes)
{
g_autofree char *dirpath = NULL;
- char *p = NULL;
struct statfs sb;
- int statfs_ret;
long long f_type = 0;
size_t i;
- dirpath = g_strdup(path);
+ if (!(dirpath = virFileGetExistingParent(path)))
+ return -1;
- statfs_ret = statfs(dirpath, &sb);
-
- while ((statfs_ret < 0) && (p != dirpath)) {
- /* Try less and less of the path until we get to a
- * directory we can stat. Even if we don't have 'x'
- * permission on any directory in the path on the NFS
- * server (assuming it's NFS), we will be able to stat the
- * mount point, and that will properly tell us if the
- * fstype is NFS.
- */
-
- if ((p = strrchr(dirpath, '/')) == NULL) {
- virReportSystemError(EINVAL,
- _("Invalid relative path '%1$s'"),
path);
- return -1;
- }
-
- if (p == dirpath)
- *(p+1) = '\0';
- else
- *p = '\0';
-
- statfs_ret = statfs(dirpath, &sb);
- }
-
- if (statfs_ret < 0) {
+ if (statfs(dirpath, &sb) < 0) {
virReportSystemError(errno,
_("cannot determine filesystem for
'%1$s'"),
path);
--
2.49.0