Whamcloud - gitweb
LU-2304 lov: check enq flags when matching top lock
authorJinshan Xiong <jinshan.xiong@intel.com>
Wed, 21 Nov 2012 18:10:42 +0000 (10:10 -0800)
committerOleg Drokin <green@whamcloud.com>
Sat, 8 Dec 2012 05:06:51 +0000 (00:06 -0500)
cld_enq_flags must be checked when matching top lock, otherwise
if a sublock is missing then it will be reenqueued with wrong enq
flags.

For LU-2304, a previous truncate to zero lock(with CEF_DISCARD_DATA)
flags was matched by not-to-zero truncate and then wrongly reenqueued
with discard flag. This caused dirty pages to be discarded on the
other clients.

Signed-off-by: Jinshan Xiong <jinshan.xiong@intel.com>
Change-Id: I290df2fdb9453c2fd7c8c3d3e7289e60bae9b095
Reviewed-on: http://review.whamcloud.com/4651
Tested-by: Hudson
Tested-by: Maloo <whamcloud.maloo@gmail.com>
Reviewed-by: Bobi Jam <bobijam@gmail.com>
Reviewed-by: Andreas Dilger <andreas.dilger@intel.com>
lustre/include/lustre_dlm.h
lustre/ldlm/ldlm_request.c
lustre/llite/llite_lib.c
lustre/llite/vvp_io.c
lustre/lov/lov_lock.c
lustre/osc/osc_lock.c

index 55a2665..3a19073 100644 (file)
@@ -990,6 +990,10 @@ extern struct obd_ops ldlm_obd_ops;
 extern char *ldlm_lockname[];
 extern char *ldlm_typename[];
 extern char *ldlm_it2str(int it);
 extern char *ldlm_lockname[];
 extern char *ldlm_typename[];
 extern char *ldlm_it2str(int it);
+
+#define LDLM_DEBUG_NOLOCK(format, a...)                 \
+        CDEBUG(D_DLMTRACE, "### " format "\n" , ##a)
+
 #ifdef LIBCFS_DEBUG
 #define ldlm_lock_debug(msgdata, mask, cdls, lock, fmt, a...) do {      \
         CFS_CHECK_STACK(msgdata, mask, cdls);                           \
 #ifdef LIBCFS_DEBUG
 #define ldlm_lock_debug(msgdata, mask, cdls, lock, fmt, a...) do {      \
         CFS_CHECK_STACK(msgdata, mask, cdls);                           \
@@ -1015,8 +1019,13 @@ void _ldlm_lock_debug(struct ldlm_lock *lock,
 #define LDLM_WARN(lock, fmt, a...)  LDLM_DEBUG_LIMIT(D_WARNING, lock, fmt, ## a)
 
 #define LDLM_DEBUG(lock, fmt, a...)   do {                                  \
 #define LDLM_WARN(lock, fmt, a...)  LDLM_DEBUG_LIMIT(D_WARNING, lock, fmt, ## a)
 
 #define LDLM_DEBUG(lock, fmt, a...)   do {                                  \
-        LIBCFS_DEBUG_MSG_DATA_DECL(msgdata, D_DLMTRACE, NULL);              \
-        ldlm_lock_debug(&msgdata, D_DLMTRACE, NULL, lock, "### " fmt , ##a);\
+       if (likely(lock != NULL)) {                                         \
+               LIBCFS_DEBUG_MSG_DATA_DECL(msgdata, D_DLMTRACE, NULL);      \
+               ldlm_lock_debug(&msgdata, D_DLMTRACE, NULL, lock,           \
+                               "### " fmt , ##a);                          \
+       } else {                                                            \
+               LDLM_DEBUG_NOLOCK("no dlm lock: " fmt, ##a);                \
+       }                                                                   \
 } while (0)
 #else /* !LIBCFS_DEBUG */
 # define LDLM_DEBUG_LIMIT(mask, lock, fmt, a...) ((void)0)
 } while (0)
 #else /* !LIBCFS_DEBUG */
 # define LDLM_DEBUG_LIMIT(mask, lock, fmt, a...) ((void)0)
@@ -1024,9 +1033,6 @@ void _ldlm_lock_debug(struct ldlm_lock *lock,
 # define LDLM_ERROR(lock, fmt, a...) ((void)0)
 #endif
 
 # define LDLM_ERROR(lock, fmt, a...) ((void)0)
 #endif
 
-#define LDLM_DEBUG_NOLOCK(format, a...)                 \
-        CDEBUG(D_DLMTRACE, "### " format "\n" , ##a)
-
 typedef int (*ldlm_processing_policy)(struct ldlm_lock *lock, __u64 *flags,
                                       int first_enq, ldlm_error_t *err,
                                       cfs_list_t *work_list);
 typedef int (*ldlm_processing_policy)(struct ldlm_lock *lock, __u64 *flags,
                                       int first_enq, ldlm_error_t *err,
                                       cfs_list_t *work_list);
index f7fc23b..36bdc5a 100644 (file)
@@ -840,7 +840,8 @@ int ldlm_cli_enqueue(struct obd_export *exp, struct ptlrpc_request **reqp,
 
                 if (einfo->ei_type == LDLM_EXTENT)
                         lock->l_req_extent = policy->l_extent;
 
                 if (einfo->ei_type == LDLM_EXTENT)
                         lock->l_req_extent = policy->l_extent;
-                LDLM_DEBUG(lock, "client-side enqueue START");
+                LDLM_DEBUG(lock, "client-side enqueue START, flags %llx\n",
+                          *flags);
         }
 
        lock->l_conn_export = exp;
         }
 
        lock->l_conn_export = exp;
index b25c913..d805a0d 100644 (file)
@@ -1410,9 +1410,9 @@ int ll_setattr_raw(struct dentry *dentry, struct iattr *attr)
         int rc = 0, rc1 = 0;
         ENTRY;
 
         int rc = 0, rc1 = 0;
         ENTRY;
 
-       CDEBUG(D_VFSTRACE, "VFS Op:inode=%lu (%p) to %llu, valid %x\n",
-               inode->i_ino,
-               inode,i_size_read(inode),
+       CDEBUG(D_VFSTRACE, "%s: setattr inode %p/fid:"DFID" from %llu to %llu, "
+               "valid %x\n", ll_get_fsname(inode->i_sb, NULL, 0), inode,
+               PFID(&lli->lli_fid), i_size_read(inode), attr->ia_size,
                attr->ia_valid);
 
         if (ia_valid & ATTR_SIZE) {
                attr->ia_valid);
 
         if (ia_valid & ATTR_SIZE) {
index f6f2271..ce492f7 100644 (file)
@@ -315,10 +315,10 @@ static int vvp_io_setattr_iter_init(const struct lu_env *env,
 static int vvp_io_setattr_lock(const struct lu_env *env,
                                const struct cl_io_slice *ios)
 {
 static int vvp_io_setattr_lock(const struct lu_env *env,
                                const struct cl_io_slice *ios)
 {
-        struct ccc_io      *cio       = ccc_env_io(env);
-        struct cl_io       *io        = ios->cis_io;
-        size_t              new_size;
-        __u32               enqflags = 0;
+       struct ccc_io *cio = ccc_env_io(env);
+       struct cl_io  *io  = ios->cis_io;
+       __u64 new_size;
+       __u32 enqflags = 0;
 
         if (cl_io_is_trunc(io)) {
                 new_size = io->u.ci_setattr.sa_attr.lvb_size;
 
         if (cl_io_is_trunc(io)) {
                 new_size = io->u.ci_setattr.sa_attr.lvb_size;
index 2424581..1faf299 100644 (file)
@@ -1007,6 +1007,11 @@ static int lov_lock_fits_into(const struct lu_env *env,
 
         ENTRY;
 
 
         ENTRY;
 
+       /* for top lock, it's necessary to match enq flags otherwise it will
+        * run into problem if a sublock is missing and reenqueue. */
+       if (need->cld_enq_flags != lov->lls_orig.cld_enq_flags)
+               return 0;
+
         if (need->cld_mode == CLM_GROUP)
                 /*
                  * always allow to match group lock.
         if (need->cld_mode == CLM_GROUP)
                 /*
                  * always allow to match group lock.
index 3a518c4..b4b5e5a 100644 (file)
@@ -1329,8 +1329,9 @@ static int osc_lock_flush(struct osc_lock *ols, int discard)
                        result = osc_cache_writeback_range(env, obj,
                                        descr->cld_start, descr->cld_end,
                                        1, discard);
                        result = osc_cache_writeback_range(env, obj,
                                        descr->cld_start, descr->cld_end,
                                        1, discard);
-                       CDEBUG(D_DLMTRACE, "write out %d pages for lock %p.\n",
-                              result, lock);
+                       LDLM_DEBUG(ols->ols_lock,
+                               "lock %p: %d pages were %s.\n", lock, result,
+                               discard ? "discarded" : "written");
                        if (result > 0)
                                result = 0;
                }
                        if (result > 0)
                                result = 0;
                }
@@ -1715,6 +1716,9 @@ int osc_lock_init(const struct lu_env *env,
                if (clk->ols_locklessable && !(enqflags & CEF_DISCARD_DATA))
                        clk->ols_flags |= LDLM_FL_DENY_ON_CONTENTION;
 
                if (clk->ols_locklessable && !(enqflags & CEF_DISCARD_DATA))
                        clk->ols_flags |= LDLM_FL_DENY_ON_CONTENTION;
 
+               LDLM_DEBUG_NOLOCK("lock %p, osc lock %p, flags %llx\n",
+                               lock, clk, clk->ols_flags);
+
                 result = 0;
         } else
                 result = -ENOMEM;
                 result = 0;
         } else
                 result = -ENOMEM;