From: Xiubo Li Date: Fri, 19 Mar 2021 08:28:57 +0000 (+0800) Subject: client: always register callbacks before mount() X-Git-Tag: v17.1.0~1946^2 X-Git-Url: http://git-server-git.apps.pok.os.sepia.ceph.com/?a=commitdiff_plain;h=35faaef499f32e2a88e022584f0b0ae11377d731;p=ceph.git client: always register callbacks before mount() Add Client::ll_register_callbacks2() support and add a new register callbacks API ceph_ll_register_callbacks2() support for libcephfs library, at the same time bump the LIBCEPHFS_VER_EXTRA up to 3. This can help get rid of the client_lock in ll_register_callbacks() and later the inode lock patches can benefit from it. Signed-off-by: Xiubo Li --- diff --git a/src/client/Client.cc b/src/client/Client.cc index 7a45461e813..7a8dee141d9 100644 --- a/src/client/Client.cc +++ b/src/client/Client.cc @@ -11013,11 +11013,11 @@ int Client::ll_statfs(Inode *in, struct statvfs *stbuf, const UserPerm& perms) return statfs(0, stbuf, perms); } -void Client::ll_register_callbacks(struct ceph_client_callback_args *args) +void Client::_ll_register_callbacks(struct ceph_client_callback_args *args) { if (!args) return; - std::scoped_lock l(client_lock); + ldout(cct, 10) << __func__ << " cb " << args->handle << " invalidate_ino_cb " << args->ino_cb << " invalidate_dentry_cb " << args->dentry_cb @@ -11049,6 +11049,23 @@ void Client::ll_register_callbacks(struct ceph_client_callback_args *args) umask_cb = args->umask_cb; } +// This is deprecated, use ll_register_callbacks2() instead. +void Client::ll_register_callbacks(struct ceph_client_callback_args *args) +{ + ceph_assert(!is_mounting() && !is_mounted() && !is_unmounting()); + + _ll_register_callbacks(args); +} + +int Client::ll_register_callbacks2(struct ceph_client_callback_args *args) +{ + if (is_mounting() || is_mounted() || is_unmounting()) + return -CEPHFS_EBUSY; + + _ll_register_callbacks(args); + return 0; +} + int Client::test_dentry_handling(bool can_invalidate) { int r = 0; diff --git a/src/client/Client.h b/src/client/Client.h index 011ff1ad07b..c0bd0108e13 100644 --- a/src/client/Client.h +++ b/src/client/Client.h @@ -623,7 +623,9 @@ public: int ll_osdaddr(int osd, uint32_t *addr); int ll_osdaddr(int osd, char* buf, size_t size); - void ll_register_callbacks(struct ceph_client_callback_args *args); + void _ll_register_callbacks(struct ceph_client_callback_args *args); + void ll_register_callbacks(struct ceph_client_callback_args *args); // deprecated + int ll_register_callbacks2(struct ceph_client_callback_args *args); int test_dentry_handling(bool can_invalidate); const char** get_tracked_conf_keys() const override; diff --git a/src/client/fuse_ll.cc b/src/client/fuse_ll.cc index c2141a00d7d..3dbd0eda092 100644 --- a/src/client/fuse_ll.cc +++ b/src/client/fuse_ll.cc @@ -1322,6 +1322,26 @@ int CephFuse::Handle::init(int argc, const char *argv[]) ceph_assert(args.allocated); // Checking fuse has realloc'd args so we can free newargv free(newargv); + + struct ceph_client_callback_args cb_args = { + handle: this, + ino_cb: client->cct->_conf.get_val("fuse_use_invalidate_cb") ? + ino_invalidate_cb : NULL, + dentry_cb: dentry_invalidate_cb, + switch_intr_cb: switch_interrupt_cb, +#if defined(__linux__) + remount_cb: remount_cb, +#endif +#if !defined(__APPLE__) + umask_cb: umask_cb, +#endif + }; + r = client->ll_register_callbacks2(&cb_args); + if (r) { + derr << "registering callbacks failed: " << r << dendl; + return r; + } + return 0; } @@ -1363,22 +1383,6 @@ int CephFuse::Handle::start() fuse_session_add_chan(se, ch); #endif - - struct ceph_client_callback_args args = { - handle: this, - ino_cb: client->cct->_conf.get_val("fuse_use_invalidate_cb") ? - ino_invalidate_cb : NULL, - dentry_cb: dentry_invalidate_cb, - switch_intr_cb: switch_interrupt_cb, -#if defined(__linux__) - remount_cb: remount_cb, -#endif -#if !defined(__APPLE__) - umask_cb: umask_cb, -#endif - }; - client->ll_register_callbacks(&args); - return 0; } diff --git a/src/include/cephfs/libcephfs.h b/src/include/cephfs/libcephfs.h index d8042f5c5fe..a7fd9b8f4fc 100644 --- a/src/include/cephfs/libcephfs.h +++ b/src/include/cephfs/libcephfs.h @@ -39,7 +39,7 @@ extern "C" { #define LIBCEPHFS_VER_MAJOR 10 #define LIBCEPHFS_VER_MINOR 0 -#define LIBCEPHFS_VER_EXTRA 2 +#define LIBCEPHFS_VER_EXTRA 3 #define LIBCEPHFS_VERSION(maj, min, extra) ((maj << 16) + (min << 8) + extra) #define LIBCEPHFS_VERSION_CODE LIBCEPHFS_VERSION(LIBCEPHFS_VER_MAJOR, LIBCEPHFS_VER_MINOR, LIBCEPHFS_VER_EXTRA) @@ -1955,6 +1955,9 @@ void ceph_finish_reclaim(struct ceph_mount_info *cmount); /** * Register a set of callbacks to be used with this cmount + * + * This is deprecated, use ceph_ll_register_callbacks2() instead. + * * @param cmount the ceph mount handle on which the cb's should be registerd * @param args callback arguments to register with the cmount * @@ -1964,6 +1967,19 @@ void ceph_finish_reclaim(struct ceph_mount_info *cmount); void ceph_ll_register_callbacks(struct ceph_mount_info *cmount, struct ceph_client_callback_args *args); +/** + * Register a set of callbacks to be used with this cmount + * @param cmount the ceph mount handle on which the cb's should be registerd + * @param args callback arguments to register with the cmount + * + * Any fields set to NULL will be ignored. There currently is no way to + * unregister these callbacks, so this is a one-way change. + * + * Returns 0 on success or -EBUSY if the cmount is mounting or already mounted. + */ +int ceph_ll_register_callbacks2(struct ceph_mount_info *cmount, + struct ceph_client_callback_args *args); + /** * Get snapshot info * diff --git a/src/libcephfs.cc b/src/libcephfs.cc index 8f88b387106..cf38fb8b83c 100644 --- a/src/libcephfs.cc +++ b/src/libcephfs.cc @@ -2075,11 +2075,17 @@ extern "C" void ceph_finish_reclaim(class ceph_mount_info *cmount) cmount->get_client()->finish_reclaim(); } +// This is deprecated, use ceph_ll_register_callbacks2 instead. extern "C" void ceph_ll_register_callbacks(class ceph_mount_info *cmount, struct ceph_client_callback_args *args) { cmount->get_client()->ll_register_callbacks(args); +} +extern "C" int ceph_ll_register_callbacks2(class ceph_mount_info *cmount, + struct ceph_client_callback_args *args) +{ + return cmount->get_client()->ll_register_callbacks2(args); } diff --git a/src/test/fs/test_ino_release_cb.cc b/src/test/fs/test_ino_release_cb.cc index 7b3fc626073..0c53fea0a32 100644 --- a/src/test/fs/test_ino_release_cb.cc +++ b/src/test/fs/test_ino_release_cb.cc @@ -56,7 +56,8 @@ int main(int argc, char *argv[]) struct ceph_client_callback_args args = { 0 }; args.ino_release_cb = cb; - ceph_ll_register_callbacks(cmount, &args); + ret = ceph_ll_register_callbacks2(cmount, &args); + assert(ret == 0); ret = ceph_mount(cmount, NULL); assert(ret >= 0);