From: Joseph Qi <joseph.qi@linux.alibaba.com>
To: sashiko-reviews@lists.linux.dev,
Andrew Morton <akpm@linux-foundation.org>,
Heming Zhao <heming.zhao@suse.com>
Cc: Mark Fasheh <mark@fasheh.com>, Joel Becker <jlbec@evilplan.org>,
"ocfs2-devel@lists.linux.dev" <ocfs2-devel@lists.linux.dev>,
"linux-kernel@vger.kernel.org" <linux-kernel@vger.kernel.org>
Subject: Re: [PATCH v2 2/3] ocfs2: use the stored hash when checking xattr bucket collision
Date: Fri, 9 Oct 2026 17:36:20 +0800 [thread overview]
Message-ID: <eb07fec3-58d5-4822-91c1-50675a8fabfa@linux.alibaba.com> (raw)
In-Reply-To: <sashiko-outbox-165102@kernel.org>
On 10/9/26 4:44 PM, sashiko-bot@kernel.org wrote:
> Thank you for your contribution! Sashiko AI review found 1 potential issue(s) to consider:
> - [High] fs/ocfs2: xattr data corruption due to stale loc.xl_entry after bucket defrag
> --
>
> commit 6247b6061c7a43f1fbd44574fe532663a6b670bc
> Author: Joseph Qi <joseph.qi@linux.alibaba.com>
>
> ocfs2: use the stored hash when checking xattr bucket collision
>
> This patch changes ocfs2_check_xattr_bucket_collision() to use the stored hash
> for existing entries when checking for bucket collisions during splits. It
> fixes an issue where unsigned hashes compared against legacy buckets reported
> no collision, leading to duplicate entries.
>
>> diff --git a/fs/ocfs2/xattr.c b/fs/ocfs2/xattr.c
>> index a428fe908116e..c5a39a7d43d07 100644
>> --- a/fs/ocfs2/xattr.c
>> +++ b/fs/ocfs2/xattr.c
>
> [ ... ]
>
>> @@ -5993,10 +5992,18 @@ static int ocfs2_xattr_set_entry_index_block(struct inode *inode,
>> * the maximum number of collisions we will allow for then is
>> * one bucket's worth, so check it here whether we need to
>> * add a new bucket for the insert.
>> + *
>> + * An existing entry keeps the hash it was stored under, and that is
>> + * the hash a split has to work with. A new entry is stored under the
>> + * unsigned one, which is what ocfs2_xa_add_entry() will write.
>> */
>> - ret = ocfs2_check_xattr_bucket_collision(inode,
>> - xs->bucket,
>> - xi->xi_name);
>> + if (xs->not_found)
>> + name_hash = ocfs2_xattr_name_hash(inode, xi->xi_name,
>> + xi->xi_name_len);
>> + else
>> + name_hash = le32_to_cpu(xs->here->xe_name_hash);
> ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>
> [Severity: High]
> If ocfs2_xattr_set_entry_bucket() fails with -ENOSPC after defragmentation,
> can this access a stale xs->here pointer?
>
> In ocfs2_xattr_set_entry_bucket(), loc.xl_entry is initialized to point
> directly to the target array element (xs->here):
>
> ocfs2_init_xattr_bucket_xa_loc(&loc, xs->bucket,
> xs->not_found ? NULL : xs->here);
>
> If ocfs2_xa_set() fails with -ENOSPC, it calls ocfs2_defrag_xattr_bucket(),
> which sorts the entries array by xe_name_hash:
>
> /* sort the entries by their name_hash. */
> sort(entries, le16_to_cpu(xh->xh_count),
> sizeof(struct ocfs2_xattr_entry),
> cmp_xe, NULL);
>
> Since sort() is unstable and hashes only cover the name suffix, identical-hash
> entries can be swapped. If they are swapped, loc.xl_entry and xs->here now
> point to the wrong xattr entry.
>
> The second ocfs2_xa_set() call then reuses the stale loc.xl_entry pointer
> without re-evaluating its position in the sorted array:
>
> ret = ocfs2_xa_set(&loc, xi, ctxt);
>
> Can this overwrite the wrong xattr's data on disk, causing data corruption?
>
> If the second ocfs2_xa_set() also fails with -ENOSPC, it returns to
> ocfs2_xattr_set_entry_index_block() where the patch now relies on the stale
> xs->here pointer to read the name_hash.
>
It seems unrelated to my patch.
Since the array is already sorted on xe_name_hash when defrag runs,
re-sorting on the same key can only permute within a run of equal
hashes. The pointer may denote a different entry, but not a different
hash.
The underlying bug is real and independent of my series: after defrag
permutes an equal-hash run, that second ocfs2_xa_set(&loc, ...) operates
on a different entry. I'd like this to be addressed in a separate
thread.
Thanks,
Joseph
next prev parent reply other threads:[~2026-10-09 9:36 UTC|newest]
Thread overview: 9+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-10-09 8:29 [PATCH v2 0/3] ocfs2: deal with legacy signed name hash values Joseph Qi
2026-10-09 8:30 ` [PATCH v2 1/3] ocfs2: deal with legacy signed dir index " Joseph Qi
2026-10-09 8:30 ` [PATCH v2 2/3] ocfs2: use the stored hash when checking xattr bucket collision Joseph Qi
[not found] ` <sashiko-outbox-165102@kernel.org>
2026-10-09 9:36 ` Joseph Qi [this message]
2026-10-09 15:05 ` Heming Zhao
2026-10-09 15:08 ` Heming Zhao
2026-10-09 8:30 ` [PATCH v2 3/3] ocfs2: deal with legacy signed xattr name hash values Joseph Qi
[not found] ` <sashiko-outbox-165103@kernel.org>
2026-10-09 9:41 ` Joseph Qi
2026-10-09 15:09 ` Heming Zhao
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=eb07fec3-58d5-4822-91c1-50675a8fabfa@linux.alibaba.com \
--to=joseph.qi@linux.alibaba.com \
--cc=akpm@linux-foundation.org \
--cc=heming.zhao@suse.com \
--cc=jlbec@evilplan.org \
--cc=linux-kernel@vger.kernel.org \
--cc=mark@fasheh.com \
--cc=ocfs2-devel@lists.linux.dev \
--cc=sashiko-reviews@lists.linux.dev \
/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.