From b2368774a01eb89981e2ceb92be9673e4b403d62 Mon Sep 17 00:00:00 2001 From: Andriy Skulysh Date: Wed, 20 Feb 2019 12:48:03 +0200 Subject: [PATCH] LU-10949 mdt: lost reference on mdt_md_root mdt_remote_object_lock_try() drops object reference in case of an error but if the request was sent to a server it is decreased again via failed_lock_cleanup() Add ldlm_created_callback. It is called after lock creation, so we can safely add a reference to l_ast_data and drop it only in BL AST handler. Cray-bug-id: LUS-7013 Change-Id: Iaf98c620804f2de4528689e44e957a9fb0073162 Signed-off-by: Andriy Skulysh Reviewed-on: https://review.whamcloud.com/34181 Tested-by: Jenkins Tested-by: Maloo Reviewed-by: Alexandr Boyko Reviewed-by: Vitaly Fertman Reviewed-by: Mike Pershin Reviewed-by: Lai Siyao Reviewed-by: Oleg Drokin --- lustre/include/lustre_dlm.h | 4 ++++ lustre/ldlm/ldlm_request.c | 4 ++++ lustre/mdt/mdt_handler.c | 9 ++++++--- 3 files changed, 14 insertions(+), 3 deletions(-) diff --git a/lustre/include/lustre_dlm.h b/lustre/include/lustre_dlm.h index 9e6ca24..15bfba2 100644 --- a/lustre/include/lustre_dlm.h +++ b/lustre/include/lustre_dlm.h @@ -594,6 +594,9 @@ typedef int (*ldlm_completion_callback)(struct ldlm_lock *lock, __u64 flags, /** Type for glimpse callback function of a lock. */ typedef int (*ldlm_glimpse_callback)(struct ldlm_lock *lock, void *data); +/** Type for created callback function of a lock. */ +typedef void (*ldlm_created_callback)(struct ldlm_lock *lock); + /** Work list for sending GL ASTs to multiple locks. */ struct ldlm_glimpse_work { struct ldlm_lock *gl_lock; /* lock to glimpse */ @@ -1163,6 +1166,7 @@ struct ldlm_enqueue_info { void *ei_cb_local_bl; /** blocking local lock callback */ void *ei_cb_cp; /** lock completion callback */ void *ei_cb_gl; /** lock glimpse callback */ + ldlm_created_callback ei_cb_created; /** lock created callback */ void *ei_cbdata; /** Data to be passed into callbacks. */ void *ei_namespace; /** lock namespace **/ u64 ei_inodebits; /** lock inode bits **/ diff --git a/lustre/ldlm/ldlm_request.c b/lustre/ldlm/ldlm_request.c index 8c4e555..d7b1b96 100644 --- a/lustre/ldlm/ldlm_request.c +++ b/lustre/ldlm/ldlm_request.c @@ -930,6 +930,10 @@ int ldlm_cli_enqueue(struct obd_export *exp, struct ptlrpc_request **reqp, lvb_len, lvb_type); if (IS_ERR(lock)) RETURN(PTR_ERR(lock)); + + if (einfo->ei_cb_created) + einfo->ei_cb_created(lock); + /* for the local lock, add the reference */ ldlm_lock_addref_internal(lock, einfo->ei_mode); ldlm_lock2handle(lock, lockh); diff --git a/lustre/mdt/mdt_handler.c b/lustre/mdt/mdt_handler.c index b1b9cc0..680ba89 100644 --- a/lustre/mdt/mdt_handler.c +++ b/lustre/mdt/mdt_handler.c @@ -2843,6 +2843,11 @@ int mdt_check_resent_lock(struct mdt_thread_info *info, return 1; } +static void mdt_remote_object_lock_created_cb(struct ldlm_lock *lock) +{ + mdt_object_get(NULL, lock->l_ast_data); +} + int mdt_remote_object_lock_try(struct mdt_thread_info *mti, struct mdt_object *o, const struct lu_fid *fid, struct lustre_handle *lh, enum ldlm_mode mode, @@ -2871,8 +2876,8 @@ int mdt_remote_object_lock_try(struct mdt_thread_info *mti, * if we cache lock, couple lock with mdt_object, so that object * can be easily found in lock ASTs. */ - mdt_object_get(mti->mti_env, o); einfo->ei_cbdata = o; + einfo->ei_cb_created = mdt_remote_object_lock_created_cb; } memset(policy, 0, sizeof(*policy)); @@ -2881,8 +2886,6 @@ int mdt_remote_object_lock_try(struct mdt_thread_info *mti, rc = mo_object_lock(mti->mti_env, mdt_object_child(o), lh, einfo, policy); - if (rc < 0 && cache) - mdt_object_put(mti->mti_env, o); /* Return successfully acquired bits to a caller */ if (rc == 0) { -- 1.8.3.1