btrfs: stripe_alloc: return a group's allocation cluster before scanning its stripes
The legacy allocator moves free space entries of a block group into an
allocation cluster -- for a metadata group, typically its whole initial
free extent -- where the group's own free space tree no longer lists
them although ctl->free_space still counts them. The stripe scan walks
that tree, so on a group armed at a runtime enable after the legacy
allocator had used it, the scan saw a fraction of the free space and
the debug check that every free byte lands in exactly one stripe
fired:
assertion failed: counted == ctl->free_space :: 0, in
fs/btrfs/free-space-cache.c:3395 (stripe_unusable_scan
counted=
1605632 != free_space=
153534464)
kernel BUG at fs/btrfs/free-space-cache.c:3395!
RIP: stripe_unusable_scan.cold
btrfs_block_group_init_stripe_unusable
stripe_alloc_sweep_groups
btrfs_enable_stripe_alloc
prop_stripe_alloc_apply
Without the assertion the group would have been armed with almost all
of its free space neither trapped nor claimable. Data groups were only
spared by the test rig: the legacy allocator clusters data only under
ssd_spread, and every stripe_alloc run so far has mounted without it.
Stripe-exclusive allocation never uses clusters, so hand the cluster's
entries back to the group before the scan, both when arming and at the
commit-time rescan (a legacy allocation already past the policy check
at the flip can still set one up). Found by stripe-meta-toggle-test.sh
on the first candidate that armed metadata groups at a runtime enable
(raid5 metadata, 4 devices, mkfs-time metadata chunk).
Assisted-by: Claude:claude-fable-5-1