From: Christoph Hellwig <hch@infradead.org>
To: Lauri Gates <lauri.gates@gmail.com>
Cc: linux-xfs@vger.kernel.org, Carlos Maiolino <cem@kernel.org>
Subject: Re: Concurrent FIEMAP on reflinked files serialises on the AGF buffer lock
Date: Mon, 2 Nov 2026 21:25:00 -0800 [thread overview]
Message-ID: <aulwLCnibXfaMzR_@infradead.org> (raw)
In-Reply-To: <20261102193533.93690-1-lauri.gates@gmail.com>
Hi Lauri,
On Mon, Nov 02, 2026 at 09:32:45PM +0200, Lauri Gates wrote:
> Hi,
>
> FIEMAP on files with XFS_DIFLAG2_REFLINK set does not scale across
> threads. For every written extent, xfs_read_iomap_begin() calls
> xfs_reflink_trim_around_shared() (IOMAP_REPORT), which goes to
> xfs_reflink_find_shared() and reads the AGF of the extent's AG with
> xfs_alloc_read_agf(pag, NULL, 0, &agbp). Concurrent callers queue on
> that buffer's b_sema. A parallel du-style scan of a reflinked tree
> stops scaling at roughly the AG count, and threads working in the same
> AG run slower than one thread alone.
FIEMAP is purely a debug interface for file system developers. So
running it in parallel for lots of files is highly unexpected and
suggests a misuse of the interface.
> My question, in more detail at the end: does reporting the shared flag
> for FIEMAP need the AGF buffer locked?
It needs to protect against agf_refcount_level changing, so yes.
In theory it would be fine with a shared lock on the AGF buffer if
we had a shared/exclusive lock on the buffers (which is something
I've wondered about a few times before), or some other high-level
synchronization against adding more reflinks.
> I ran into this adding a shared-block mode to dust, a du clone, which
> FIEMAPs every file and counts FIEMAP_EXTENT_SHARED extents once.
> Inodes without the reflink flag return early and are unaffected.
Ok, so this is the use case. The more efficient way to do this
would be to subtract the multiple mapped extents based on the
refcount btree, i.e.
for each AG (and RTG with rtreflink):
for each entry in the (rt)refcountbt:
subtract rc_blockcount * (rc_refcount - 1);
We'd need a new ioctl for that, but it should be pretty easy.
The major downside is that this only works for whole-device du,
but then also any other version would have a really hard time figuring
out what to do with reflinks the span the reported/not reported
boundary.
> I am not suggesting dropping the flag. Commit 5f9268ca53ac ("xfs:
> don't bother looking at the refcount tree for reads") kept
> IOMAP_REPORT on the refcount lookup deliberately, and Dave described
> the shared flag as a field diagnostic for reflinked files:
> https://lore.kernel.org/all/20210124214346.GC4626@dread.disaster.area/
IOMAP_REPORT/FIEMAP reporting the shared flag is probably exactly what
your tool relies on...
next prev parent reply other threads:[~2026-11-03 5:25 UTC|newest]
Thread overview: 9+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-11-02 19:32 Concurrent FIEMAP on reflinked files serialises on the AGF buffer lock Lauri Gates
2026-11-03 5:25 ` Christoph Hellwig [this message]
2026-11-04 12:41 ` Lauri Gates
2026-11-04 21:11 ` Dave Chinner
2026-11-06 15:21 ` Christoph Hellwig
2026-11-04 21:04 ` Dave Chinner
2026-11-06 12:23 ` Lauri Gates
2026-11-06 15:20 ` Christoph Hellwig
2026-11-06 20:40 ` Lauri Gates
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=aulwLCnibXfaMzR_@infradead.org \
--to=hch@infradead.org \
--cc=cem@kernel.org \
--cc=lauri.gates@gmail.com \
--cc=linux-xfs@vger.kernel.org \
/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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox