Whamcloud - gitweb
LU-7619 obdclass: protect REFASSERT() with lu_ref::lf_guard 56/17756/2
authorBruno Faccini <bruno.faccini@intel.com>
Wed, 30 Dec 2015 16:39:48 +0000 (17:39 +0100)
committerOleg Drokin <oleg.drokin@intel.com>
Mon, 11 Jul 2016 23:54:11 +0000 (23:54 +0000)
Some REFASSERT()s have been added by previous changes, but not
under required lu_ref::lf_guard spin-lock protection.
This can cause unexpected "self" dead-lock situations (vs
LBUG/ASSERT!!) upon lu_ref failure detection.

Signed-off-by: Bruno Faccini <bruno.faccini@intel.com>
Change-Id: If23d43f6fca196a33602b6bb8f051c0a4e26a300
Reviewed-on: http://review.whamcloud.com/17756
Tested-by: Jenkins
Tested-by: Maloo <hpdd-maloo@intel.com>
Reviewed-by: Andreas Dilger <andreas.dilger@intel.com>
Reviewed-by: Mike Pershin <mike.pershin@intel.com>
lustre/obdclass/lu_ref.c

index 3308b17..4ebb29b 100644 (file)
@@ -138,8 +138,10 @@ void lu_ref_init_loc(struct lu_ref *ref, const char *func, const int line)
 
 void lu_ref_fini(struct lu_ref *ref)
 {
+       spin_lock(&ref->lf_guard);
        REFASSERT(ref, list_empty(&ref->lf_list));
        REFASSERT(ref, ref->lf_refs == 0);
+       spin_unlock(&ref->lf_guard);
        spin_lock(&lu_ref_refs_guard);
        list_del_init(&ref->lf_linkage);
        spin_unlock(&lu_ref_refs_guard);
@@ -260,9 +262,8 @@ void lu_ref_set_at(struct lu_ref *ref, struct lu_ref_link *link,
                   const char *scope,
                   const void *source0, const void *source1)
 {
-       REFASSERT(ref, link != NULL && !IS_ERR(link));
-
        spin_lock(&ref->lf_guard);
+       REFASSERT(ref, link != NULL && !IS_ERR(link));
        REFASSERT(ref, link->ll_ref == ref);
        REFASSERT(ref, lu_ref_link_eq(link, scope, source0));
        link->ll_source = source1;
@@ -272,8 +273,8 @@ void lu_ref_set_at(struct lu_ref *ref, struct lu_ref_link *link,
 void lu_ref_del_at(struct lu_ref *ref, struct lu_ref_link *link,
                   const char *scope, const void *source)
 {
-       REFASSERT(ref, link != NULL && !IS_ERR(link));
        spin_lock(&ref->lf_guard);
+       REFASSERT(ref, link != NULL && !IS_ERR(link));
        REFASSERT(ref, link->ll_ref == ref);
        REFASSERT(ref, lu_ref_link_eq(link, scope, source));
        list_del(&link->ll_linkage);