Whamcloud - gitweb
LU-18557 ldlm: save ldlm namespace ops for use 32/57432/3
authorAlex Zhuravlev <bzzz@whamcloud.com>
Sat, 14 Dec 2024 11:49:51 +0000 (14:49 +0300)
committerOleg Drokin <green@whamcloud.com>
Fri, 28 Feb 2025 08:12:09 +0000 (08:12 +0000)
save ldlm namespace ops for use as __ldlm_resource_putref_final() can
initiate namespace release in a separate thread which in turn will
invalidate the structure pointing to the namespace's ops.

Signed-off-by: Alex Zhuravlev <bzzz@whamcloud.com>
Change-Id: If3ddc032b21806046fede09d40a4df78d441138d
Reviewed-on: https://review.whamcloud.com/c/fs/lustre-release/+/57432
Tested-by: jenkins <devops@whamcloud.com>
Tested-by: Maloo <maloo@whamcloud.com>
Reviewed-by: Alexey Lyashkov <alexey.lyashkov@hpe.com>
Reviewed-by: Oleg Drokin <green@whamcloud.com>
Reviewed-by: Mikhail Pershin <mpershin@whamcloud.com>
lustre/ldlm/ldlm_resource.c

index 440c3d1..017f8a5 100644 (file)
@@ -1605,6 +1605,7 @@ static void __ldlm_resource_putref_final(struct cfs_hash_bd *bd,
 /* Returns 1 if the resource was freed, 0 if it remains. */
 int ldlm_resource_putref(struct ldlm_resource *res)
 {
+       struct ldlm_valblock_ops *ns_lvbo;
        struct ldlm_namespace *ns;
        struct cfs_hash_bd bd;
        int refcount;
@@ -1612,6 +1613,9 @@ int ldlm_resource_putref(struct ldlm_resource *res)
        if (refcount_dec_not_one(&res->lr_refcount))
                return 0;
        ns = ldlm_res_to_ns(res);
+       /* save ops as __ldlm_resource_putref_final() may
+        * initiate namespace release in a separate thread */
+       ns_lvbo = ns->ns_lvbo;
        refcount = refcount_read(&res->lr_refcount);
        LASSERT(refcount < LI_POISON);
 
@@ -1622,8 +1626,8 @@ int ldlm_resource_putref(struct ldlm_resource *res)
        if (cfs_hash_bd_dec_and_lock(ns->ns_rs_hash, &bd, &res->lr_refcount)) {
                __ldlm_resource_putref_final(&bd, res);
                cfs_hash_bd_unlock(ns->ns_rs_hash, &bd, 1);
-               if (ns->ns_lvbo && ns->ns_lvbo->lvbo_free)
-                       ns->ns_lvbo->lvbo_free(res);
+               if (ns_lvbo && ns_lvbo->lvbo_free)
+                       ns_lvbo->lvbo_free(res);
                ldlm_resource_free(res);
                return 1;
        }