From: Joel Becker <Joel.Becker@oracle.com>
To: ocfs2-devel@oss.oracle.com
Subject: [Ocfs2-devel] [PATCH] ocfs2: Add lockdep annotations
Date: Wed, 3 Jun 2009 09:31:56 -0700 [thread overview]
Message-ID: <20090603163155.GD24166@mail.oracle.com> (raw)
In-Reply-To: <1243945445-25847-8-git-send-email-jack@suse.cz>
On Tue, Jun 02, 2009 at 02:24:05PM +0200, Jan Kara wrote:
> Add lockdep support to OCFS2. The support also covers all of the cluster
> locks except for open locks, journal locks, and local quotafile locks. These
> are special because they are acquired for a node, not for a particular process
> and lockdep cannot deal with such type of locking.
I like the idea of ocfs2 having lockdep on everything.
> -static void ocfs2_cluster_unlock(struct ocfs2_super *osb,
> - struct ocfs2_lock_res *lockres,
> - int level);
> +static void __ocfs2_cluster_unlock(struct ocfs2_super *osb,
> + struct ocfs2_lock_res *lockres,
> + int level, unsigned long ip);
> +static inline void ocfs2_cluster_unlock(struct ocfs2_super *osb,
> + struct ocfs2_lock_res *lockres,
> + int level)
> +{
> + __ocfs2_cluster_unlock(osb, lockres, level, _RET_IP_);
> +}
I don't know why 'ip' needs to be part of the function prototype
- every place you use it, you just pass _RET_IP_.
> @@ -1239,11 +1256,21 @@ static int ocfs2_wait_for_mask_interruptible(struct ocfs2_mask_waiter *mw,
> return ret;
> }
>
> -static int ocfs2_cluster_lock(struct ocfs2_super *osb,
> - struct ocfs2_lock_res *lockres,
> - int level,
> - u32 lkm_flags,
> - int arg_flags)
> +#ifdef CONFIG_DEBUG_LOCK_ALLOC
> +static int __ocfs2_cluster_lock(struct ocfs2_super *osb,
> + struct ocfs2_lock_res *lockres,
> + int level,
> + u32 lkm_flags,
> + int arg_flags,
> + int l_subclass,
> + unsigned long ip)
> +#else
> +static int __ocfs2_cluster_lock(struct ocfs2_super *osb,
> + struct ocfs2_lock_res *lockres,
> + int level,
> + u32 lkm_flags,
> + int arg_flags)
> +#endif
> {
> struct ocfs2_mask_waiter mw;
> int wait, catch_signals = !(osb->s_mount_opt & OCFS2_MOUNT_NOINTR);
> @@ -1386,13 +1413,45 @@ out:
> }
> ocfs2_update_lock_stats(lockres, level, &mw, ret);
>
> +#ifdef CONFIG_DEBUG_LOCK_ALLOC
> + if (!ret && lockres->l_lockdep_map.key != NULL) {
> + if (level == DLM_LOCK_PR)
> + rwsem_acquire_read(&lockres->l_lockdep_map, l_subclass,
> + !!(arg_flags & OCFS2_META_LOCK_NOQUEUE), ip);
> + else
> + rwsem_acquire(&lockres->l_lockdep_map, l_subclass,
> + !!(arg_flags & OCFS2_META_LOCK_NOQUEUE), ip);
> + }
> +#endif
> mlog_exit(ret);
> return ret;
> }
Here again you've wrapped an ifdef around whether 'ip' is in the
argument list or not. Since it's always _RET_IP_, why not just leave it
out of the argument list and just pas _RET_IP_ to the rwsem_acquire
calls? That also eliminates the ugly ifdefs and need for
__ocfs2_cluster_lock().
> +#ifdef CONFIG_DEBUG_LOCK_ALLOC
> +static void __ocfs2_cluster_unlock(struct ocfs2_super *osb,
> + struct ocfs2_lock_res *lockres,
> + int level,
> + unsigned long ip)
> +#else
> +static void __ocfs2_cluster_unlock(struct ocfs2_super *osb,
> + struct ocfs2_lock_res *lockres,
> + int level)
> +#endif
> {
> unsigned long flags;
>
> @@ -1401,6 +1460,10 @@ static void ocfs2_cluster_unlock(struct ocfs2_super *osb,
> ocfs2_dec_holders(lockres, level);
> ocfs2_downconvert_on_unlock(osb, lockres);
> spin_unlock_irqrestore(&lockres->l_lock, flags);
> +#ifdef CONFIG_DEBUG_LOCK_ALLOC
> + if (lockres->l_lockdep_map.key != NULL)
> + rwsem_release(&lockres->l_lockdep_map, 1, ip);
> +#endif
> mlog_exit_void();
> }
Same here.
> @@ -2145,10 +2208,11 @@ static int ocfs2_assign_bh(struct inode *inode,
> * returns < 0 error if the callback will never be called, otherwise
> * the result of the lock will be communicated via the callback.
> */
> -int ocfs2_inode_lock_full(struct inode *inode,
> - struct buffer_head **ret_bh,
> - int ex,
> - int arg_flags)
> +int ocfs2_inode_lock_full_nested(struct inode *inode,
> + struct buffer_head **ret_bh,
> + int ex,
> + int arg_flags,
> + int subclass)
> {
> int status, level, acquired;
> u32 dlm_flags;
> @@ -2186,7 +2250,12 @@ int ocfs2_inode_lock_full(struct inode *inode,
> if (arg_flags & OCFS2_META_LOCK_NOQUEUE)
> dlm_flags |= DLM_LKF_NOQUEUE;
>
> +#ifdef CONFIG_DEBUG_LOCK_ALLOC
> + status = __ocfs2_cluster_lock(osb, lockres, level, dlm_flags,
> + arg_flags, subclass, _RET_IP_);
> +#else
> status = ocfs2_cluster_lock(osb, lockres, level, dlm_flags, arg_flags);
> +#endif
This hunk wouldn't be necessary either.
> --- a/fs/ocfs2/inode.c
> +++ b/fs/ocfs2/inode.c
> @@ -215,6 +215,8 @@ bail:
> static int ocfs2_init_locked_inode(struct inode *inode, void *opaque)
> {
> struct ocfs2_find_inode_args *args = opaque;
> + static struct lock_class_key ocfs2_quota_ip_alloc_sem_key,
> + ocfs2_file_ip_alloc_sem_key;
>
> mlog_entry("inode = %p, opaque = %p\n", inode, opaque);
>
> @@ -223,6 +225,15 @@ static int ocfs2_init_locked_inode(struct inode *inode, void *opaque)
> if (args->fi_sysfile_type != 0)
> lockdep_set_class(&inode->i_mutex,
> &ocfs2_sysfile_lock_key[args->fi_sysfile_type]);
> + if (args->fi_sysfile_type == USER_QUOTA_SYSTEM_INODE ||
> + args->fi_sysfile_type == GROUP_QUOTA_SYSTEM_INODE ||
> + args->fi_sysfile_type == LOCAL_USER_QUOTA_SYSTEM_INODE ||
> + args->fi_sysfile_type == LOCAL_GROUP_QUOTA_SYSTEM_INODE)
> + lockdep_set_class(&OCFS2_I(inode)->ip_alloc_sem,
> + &ocfs2_quota_ip_alloc_sem_key);
> + else
> + lockdep_set_class(&OCFS2_I(inode)->ip_alloc_sem,
> + &ocfs2_file_ip_alloc_sem_key);
These keys don't need to be intialized?
> diff --git a/fs/ocfs2/inode.h b/fs/ocfs2/inode.h
> index ea71525..7096516 100644
> --- a/fs/ocfs2/inode.h
> +++ b/fs/ocfs2/inode.h
> @@ -109,6 +109,14 @@ struct ocfs2_inode_info
> /* Indicates that the metadata cache should be used as an array. */
> #define OCFS2_INODE_CACHE_INLINE 0x00000080
>
> +/* Locking subclasses of inode cluster lock */
> +enum {
> + OI_LS_NORMAL,
> + OI_LS_PARENT,
> + OI_LS_RENAME1,
> + OI_LS_RENAME2,
> +};
> +
I couldn't see where OI_LS_NORMAL was ever used, until I
realized that your #define of ocfs2_inode_lock_full hardcodes
OI_LS_NORMAL as '0'. It should really use the subclass name, right?
Joel
--
"Senator let's be sincere,
As much as you can."
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker at oracle.com
Phone: (650) 506-8127
next prev parent reply other threads:[~2009-06-03 16:31 UTC|newest]
Thread overview: 20+ messages / expand[flat|nested] mbox.gz Atom feed top
2009-06-02 12:23 [Ocfs2-devel] [PATCH 0/7] [RESEND] Fix some deadlocks in quota code and implement lockdep for cluster locks Jan Kara
2009-06-02 12:23 ` [Ocfs2-devel] [PATCH] ocfs2: Fix possible deadlock in ocfs2_global_read_dquot() Jan Kara
2009-06-03 0:15 ` Joel Becker
2009-06-03 13:31 ` Jan Kara
2009-06-02 12:24 ` [Ocfs2-devel] [PATCH] ocfs2: Fix lock inversion in ocfs2_local_read_info() Jan Kara
2009-06-02 12:24 ` [Ocfs2-devel] [PATCH] ocfs2: Fix possible deadlock with quotas in ocfs2_setattr() Jan Kara
2009-06-02 12:24 ` [Ocfs2-devel] [PATCH] ocfs2: Fix possible deadlock in quota recovery Jan Kara
2009-06-02 12:24 ` [Ocfs2-devel] [PATCH] ocfs2: Correct ordering of ip_alloc_sem and localloc locks for directories Jan Kara
2009-06-03 21:05 ` Mark Fasheh
2009-06-02 12:24 ` [Ocfs2-devel] [PATCH] vfs: Set special lockdep map for dirs only if not set by fs Jan Kara
2009-06-02 12:53 ` Peter Zijlstra
2009-06-02 12:24 ` [Ocfs2-devel] [PATCH] ocfs2: Add lockdep annotations Jan Kara
2009-06-03 16:31 ` Joel Becker [this message]
2009-06-03 21:48 ` Jan Kara
2009-06-03 22:42 ` Joel Becker
2009-06-04 10:22 ` Jan Kara
2009-06-02 18:43 ` [Ocfs2-devel] [PATCH 0/7] [RESEND] Fix some deadlocks in quota code and implement lockdep for cluster locks Joel Becker
2009-06-04 2:26 ` Joel Becker
2009-06-04 10:09 ` Jan Kara
2009-06-09 17:05 ` Joel Becker
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20090603163155.GD24166@mail.oracle.com \
--to=joel.becker@oracle.com \
--cc=ocfs2-devel@oss.oracle.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.