All of lore.kernel.org
 help / color / mirror / Atom feed
From: Al Viro <viro@zeniv.linux.org.uk>
To: Jianzhou Zhao <luckd0g@163.com>
Cc: linux-kernel@vger.kernel.org, brauner@kernel.org, jack@suse.cz,
	linux-fsdevel@vger.kernel.org
Subject: Re: KCSAN: data-race in __d_drop / retain_dentry
Date: Thu, 9 Apr 2026 00:34:10 +0100	[thread overview]
Message-ID: <20260408233410.GN3836593@ZenIV> (raw)
In-Reply-To: <20260408231240.GM3836593@ZenIV>

On Thu, Apr 09, 2026 at 12:12:40AM +0100, Al Viro wrote:
> On Wed, Mar 11, 2026 at 04:02:41PM +0800, Jianzhou Zhao wrote:
> 
> > Execution Flow & Code Context
> > When a dentry receives its final decrement during a path operation (e.g., inside `dput`), its lifecycle might traverse `__dentry_kill()` leading to `__d_drop()`. Here, VFS manually eradicates the dentry from the hash list by assigning `NULL` to the internal double-linked list pointer tracker `pprev`:
> > ```c
> > // fs/dcache.c
> > void __d_drop(struct dentry *dentry)
> > {
> > 	if (!d_unhashed(dentry)) {
> > 		___d_drop(dentry);
> > 		...
> > 		dentry->d_hash.pprev = NULL; // <-- Plain concurrent write
> > 		write_seqcount_invalidate(&dentry->d_seq);
> > 	}
> > }
> > ```
> > 
> > Simultaneously, another thread undergoing an optimistic lockless `dput`
> 
> Without having held the reference it's dropping?

Note that if the sequence is
A:	fast_dput(): count 1->0
B:	grab reference, count 0->1
B:	drop, reference, count 1->0, grab ->d_lock and proceedi to __dentry_kill()
B:	in __dentry_kill() set count negative
B:	in __dentry_kill() clear ->d_hash.pprev
A:	call retain_dentry()
which is legitimate, not noticing d_unhashed() in retain_dentry() is fine -
fast_dput() will proceed to
	spin_lock(&dentry->d_lock);
	if (dentry->d_lockref.count || retain_dentry(dentry, true)) {
notice that ->d_lockref.count is negative and bugger off to
		spin_unlock(&dentry->d_lock);
		return true;
with rcu_read_lock() still held, same as it would if retain_dentry()
had returned true.

See the comments in fast_dput(), specifically
	/*
	 * Did somebody else grab a reference to it in the meantime, and
	 * we're no longer the last user after all? Alternatively, somebody
	 * else could have killed it and marked it dead. Either way, we
	 * don't need to do anything else.
	 */

      reply	other threads:[~2026-04-08 23:30 UTC|newest]

Thread overview: 10+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-03-11  8:02 KCSAN: data-race in __d_drop / retain_dentry Jianzhou Zhao
2026-03-11  7:55 ` KCSAN: data-race in step_into_slowpath / vfs_unlink Jianzhou Zhao
2026-03-11  7:49   ` KCSAN: data-race in __remove_assoc_queue / mark_buffer_dirty_inode Jianzhou Zhao
2026-03-11  2:54     ` KCSAN: data-race in path_lookupat / vfs_rename Jianzhou Zhao
2026-03-11 10:38       ` KCSAN: data-race in __d_drop / retain_dentry Christian Brauner
2026-04-08 23:04       ` KCSAN: data-race in path_lookupat / vfs_rename Al Viro
2026-04-08 23:06         ` Al Viro
2026-03-17 12:37     ` KCSAN: data-race in __remove_assoc_queue / mark_buffer_dirty_inode Jan Kara
2026-04-08 23:12 ` KCSAN: data-race in __d_drop / retain_dentry Al Viro
2026-04-08 23:34   ` Al Viro [this message]

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=20260408233410.GN3836593@ZenIV \
    --to=viro@zeniv.linux.org.uk \
    --cc=brauner@kernel.org \
    --cc=jack@suse.cz \
    --cc=linux-fsdevel@vger.kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=luckd0g@163.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.