]> git.apps.os.sepia.ceph.com Git - ceph-ci.git/commitdiff
ceph-fuse: add connection args parsing support for libfuse > 3.0
authorXiubo Li <xiubli@redhat.com>
Tue, 5 May 2020 04:17:47 +0000 (00:17 -0400)
committerXiubo Li <xiubli@redhat.com>
Wed, 8 Jul 2020 07:27:23 +0000 (03:27 -0400)
Since 3.0 some options are moved to connection part.

The following options are recognized and should be parsed and
applied to the connection:

    -o max_write=N         sets conn->max_write
    -o max_readahead=N     sets conn->max_readahead
    -o max_background=N    sets conn->max_background
    -o congestion_threshold=N  sets conn->congestion_threshold
    -o async_read          sets FUSE_CAP_ASYNC_READ in conn->want
    -o sync_read           unsets FUSE_CAP_ASYNC_READ in conn->want
    -o atomic_o_trunc      sets FUSE_CAP_ATOMIC_O_TRUNC in conn->want
    -o no_remote_lock      Equivalent to -o no_remote_flock,no_remote_posix_lock
    -o no_remote_flock     Unsets FUSE_CAP_FLOCK_LOCKS in conn->want
    -o no_remote_posix_lock  Unsets FUSE_CAP_POSIX_LOCKS in conn->want
    -o [no_]splice_write     (un-)sets FUSE_CAP_SPLICE_WRITE in conn->want
    -o [no_]splice_move      (un-)sets FUSE_CAP_SPLICE_MOVE in conn->want
    -o [no_]splice_read      (un-)sets FUSE_CAP_SPLICE_READ in conn->want
    -o [no_]auto_inval_data  (un-)sets FUSE_CAP_AUTO_INVAL_DATA in conn->want
    -o readdirplus=no        unsets FUSE_CAP_READDIRPLUS in conn->want
    -o readdirplus=yes       sets FUSE_CAP_READDIRPLUS and unsets
                             FUSE_CAP_READDIRPLUS_AUTO in conn->want
    -o readdirplus=auto      sets FUSE_CAP_READDIRPLUS and
                             FUSE_CAP_READDIRPLUS_AUTO in conn->want
    -o [no_]async_dio        (un-)sets FUSE_CAP_ASYNC_DIO in conn->want
    -o [no_]writeback_cache  (un-)sets FUSE_CAP_WRITEBACK_CACHE in conn->want
    -o time_gran=N           sets conn->time_gran

Fixes: https://tracker.ceph.com/issues/45267
Signed-off-by: Xiubo Li <xiubli@redhat.com>
src/client/fuse_ll.cc

index 16f4d12abd0d518e6b30b15bac5ffd324b2240ba..7cec8d70b9be28b325d9644e4b8fb3968ef5538a 100644 (file)
@@ -88,6 +88,7 @@ public:
   struct fuse_session *se;
 #if FUSE_VERSION >= FUSE_MAKE_VERSION(3, 0)
   struct fuse_cmdline_opts opts;
+  struct fuse_conn_info_opts *conn_opts;
 #else
   struct fuse_chan *ch;
   char *mountpoint;
@@ -989,6 +990,10 @@ static void do_init(void *data, fuse_conn_info *conn)
   CephFuse::Handle *cfuse = (CephFuse::Handle *)data;
   Client *client = cfuse->client;
 
+#if FUSE_VERSION >= FUSE_MAKE_VERSION(3, 0)
+  fuse_apply_conn_info_opts(cfuse->conn_opts, conn);
+#endif
+
 #if !defined(__APPLE__)
   if (!client->fuse_default_permissions && client->ll_handle_umask()) {
     // apply umask in userspace if posix acl is enabled
@@ -1105,6 +1110,8 @@ void CephFuse::Handle::finalize()
     fuse_session_unmount(se);
     fuse_session_destroy(se);
   }
+  if (conn_opts)
+    free(conn_opts);
   if (opts.mountpoint)
     free(opts.mountpoint);
 #else
@@ -1132,7 +1139,7 @@ int CephFuse::Handle::init(int argc, const char *argv[])
 
   // set up fuse argc/argv
   int newargc = 0;
-  const char **newargv = (const char **) malloc((argc + 10) * sizeof(char *));
+  const char **newargv = (const char **) malloc((argc + 11) * sizeof(char *));
   if(!newargv)
     return ENOMEM;
 
@@ -1146,11 +1153,11 @@ int CephFuse::Handle::init(int argc, const char *argv[])
 #if FUSE_VERSION < FUSE_MAKE_VERSION(3, 0)
   auto fuse_big_writes = client->cct->_conf.get_val<bool>(
     "fuse_big_writes");
+#endif
   auto fuse_max_write = client->cct->_conf.get_val<Option::size_t>(
     "fuse_max_write");
   auto fuse_atomic_o_trunc = client->cct->_conf.get_val<bool>(
     "fuse_atomic_o_trunc");
-#endif
   auto fuse_debug = client->cct->_conf.get_val<bool>(
     "fuse_debug");
 
@@ -1168,6 +1175,7 @@ int CephFuse::Handle::init(int argc, const char *argv[])
     newargv[newargc++] = "-o";
     newargv[newargc++] = "big_writes";
   }
+#endif
   if (fuse_max_write > 0) {
     char strsplice[65];
     newargv[newargc++] = "-o";
@@ -1178,7 +1186,6 @@ int CephFuse::Handle::init(int argc, const char *argv[])
     newargv[newargc++] = "-o";
     newargv[newargc++] = "atomic_o_trunc";
   }
-#endif
 #endif
   if (fuse_debug)
     newargv[newargc++] = "-d";
@@ -1201,6 +1208,17 @@ int CephFuse::Handle::init(int argc, const char *argv[])
     return EINVAL;
   }
 
+#if FUSE_VERSION >= FUSE_MAKE_VERSION(3, 0)
+  derr << "init, args.argv = " << args.argv << " args.argc=" << args.argc << dendl;
+  conn_opts = fuse_parse_conn_info_opts(&args);
+  if (!conn_opts) {
+    derr << "fuse_parse_conn_info_opts failed" << dendl;
+    fuse_opt_free_args(&args);
+    free(newargv);
+    return EINVAL;
+  }
+#endif
+
   ceph_assert(args.allocated);  // Checking fuse has realloc'd args so we can free newargv
   free(newargv);
   return 0;
@@ -1210,6 +1228,10 @@ int CephFuse::Handle::start()
 {
 #if FUSE_VERSION >= FUSE_MAKE_VERSION(3, 0)
   se = fuse_session_new(&args, &fuse_ll_oper, sizeof(fuse_ll_oper), this);
+  if (!se) {
+    derr << "fuse_session_new failed" << dendl;
+    return EDOM;
+  }
 #else
   ch = fuse_mount(mountpoint, &args);
   if (!ch) {
@@ -1218,11 +1240,11 @@ int CephFuse::Handle::start()
   }
 
   se = fuse_lowlevel_new(&args, &fuse_ll_oper, sizeof(fuse_ll_oper), this);
-#endif
   if (!se) {
     derr << "fuse_lowlevel_new failed" << dendl;
     return EDOM;
   }
+#endif
 
   signal(SIGTERM, SIG_DFL);
   signal(SIGINT, SIG_DFL);