[Virtio-fs] [PATCH v2] virtiofsd: Prevent multiply running with same vhost_user_socket

Masayoshi Mizuma msys.mizuma at gmail.com
Sun Aug 11 22:55:34 UTC 2019


From: Masayoshi Mizuma <m.mizuma at jp.fujitsu.com>

virtiofsd can run multiply even if the vhost_user_socket is
same path.

  ]# ./virtiofsd -o vhost_user_socket=/tmp/vhostqemu -o source=/tmp/share &
  [1] 244965
  virtio_session_mount: Waiting for vhost-user socket connection...
  ]# ./virtiofsd -o vhost_user_socket=/tmp/vhostqemu -o source=/tmp/share &
  [2] 244966
  virtio_session_mount: Waiting for vhost-user socket connection...
  ]#

The user will get confused about the situation and maybe the cause of the
unexpected problem. So it's better to prevent the multiple running.

Create a regular file under localstatedir directory to exclude the
vhost_user_socket. To create and lock the file, use qemu_write_pidfile()
because the API has some sanity checks and file lock.

Signed-off-by: Masayoshi Mizuma <m.mizuma at jp.fujitsu.com>
---
 contrib/virtiofsd/fuse_i.h        |  1 +
 contrib/virtiofsd/fuse_lowlevel.c |  3 ++
 contrib/virtiofsd/fuse_virtio.c   | 50 +++++++++++++++++++++++++++++++
 3 files changed, 54 insertions(+)

diff --git a/contrib/virtiofsd/fuse_i.h b/contrib/virtiofsd/fuse_i.h
index ff6e1b75ba..d31c675469 100644
--- a/contrib/virtiofsd/fuse_i.h
+++ b/contrib/virtiofsd/fuse_i.h
@@ -72,6 +72,7 @@ struct fuse_session {
         char *vu_socket_path;
         int   vu_listen_fd;
         int   vu_socketfd;
+        char *vu_socket_lock_file;
         struct fv_VuDev *virtio_dev;
 };
 
diff --git a/contrib/virtiofsd/fuse_lowlevel.c b/contrib/virtiofsd/fuse_lowlevel.c
index 8adc4b1ab8..ab18b86435 100644
--- a/contrib/virtiofsd/fuse_lowlevel.c
+++ b/contrib/virtiofsd/fuse_lowlevel.c
@@ -2587,6 +2587,9 @@ void fuse_session_destroy(struct fuse_session *se)
 	free(se->vu_socket_path);
 	se->vu_socket_path = NULL;
 
+	unlink(se->vu_socket_lock_file);
+	free(se->vu_socket_lock_file);
+
 	free(se);
 }
 
diff --git a/contrib/virtiofsd/fuse_virtio.c b/contrib/virtiofsd/fuse_virtio.c
index 083e4fc317..4999f95b63 100644
--- a/contrib/virtiofsd/fuse_virtio.c
+++ b/contrib/virtiofsd/fuse_virtio.c
@@ -32,6 +32,9 @@
 
 #include "contrib/libvhost-user/libvhost-user.h"
 
+#include "qemu/osdep.h"
+#include "qapi/error.h"
+
 struct fv_VuDev;
 struct fv_QueueInfo {
         pthread_t thread;
@@ -862,6 +865,47 @@ int virtio_loop(struct fuse_session *se)
        return 0;
 }
 
+static void strreplace(char *s, char old, char new)
+{
+        for (; *s; ++s)
+                if (*s == old)
+                        *s = new;
+}
+
+static int fv_create_socket_lock_file(struct fuse_session *se)
+{
+        char *dir, *socket_name;
+        Error *local_err = NULL;
+
+        dir = qemu_get_local_state_pathname("run/virtiofsd");
+
+        if (g_mkdir_with_parents(dir, S_IRWXU) < -1) {
+                fuse_err("%s: Failed to create directory %s: %s",
+                        __func__, dir, strerror(errno));
+                return -1;
+        }
+
+        socket_name = malloc(strlen(se->vu_socket_path) + 1);
+        memset(socket_name, 0, strlen(se->vu_socket_path) + 1);
+        memcpy(socket_name, se->vu_socket_path, strlen(se->vu_socket_path));
+        strreplace(socket_name, '/', '.');
+
+        se->vu_socket_lock_file = malloc(NAME_MAX);
+        memset(se->vu_socket_lock_file, 0, NAME_MAX);
+        snprintf(se->vu_socket_lock_file, NAME_MAX, "%s/%s.pid",
+			dir, socket_name);
+
+        if (!qemu_write_pidfile(se->vu_socket_lock_file, &local_err)) {
+                error_report_err(local_err);
+                return -1;
+        }
+
+        free(socket_name);
+        g_free(dir);
+
+        return 0;
+}
+
 static int fv_create_listen_socket(struct fuse_session *se)
 {
         struct sockaddr_un un;
@@ -876,6 +920,12 @@ static int fv_create_listen_socket(struct fuse_session *se)
                 return -1;
         }
 
+        /* Check the vu_socket_path is already used */
+        if (fv_create_socket_lock_file(se) == -1) {
+                fuse_err("%s: Socket lock file creation failed\n", __func__);
+                return -1;
+        }
+
         /* Create the Unix socket to communicate with qemu
          * based on QEMU's vhost-user-bridge
          */
-- 
2.18.1




More information about the Virtio-fs mailing list