kmem_cache_free(btrfs_free_space_cachep, info);
out:
/*
- * Whole stripes wholly inside the returned range are trivially
- * fully free and claimable, whatever merging did around them.
- * Boundary fragments may complete stripes too; not detecting that
- * errs claimable-low, and the rescan corrects it.
+ * Do NOT incrementally credit newly-freed whole stripes here. Add paths
+ * re-add space that a low-level remove never de-credited -- the async
+ * discard trim (unlink_free_space / bitmap_clear_bits + do_trimming's
+ * re-add) and btrfs_remove_free_space's middle-split tail -- so crediting
+ * on add double-counts and stripe_claimable drifts ABOVE the authoritative
+ * scan. That is the dangerous direction: once admission gates on the
+ * counter, an over-count admits reservations against phantom supply that
+ * writeback then drops. The incremental rules now only ever DEBIT
+ * (removes/claims, which err low); the per-commit rescan is the sole
+ * upward correction, so the counter can only under-count (early, clean
+ * write()-time ENOSPC) -- never over-count.
*/
- if (!ret && btrfs_is_stripe_alloc_bg(block_group))
- stripe_claimable_mod(block_group,
- stripe_interior_bytes(block_group,
- offset, bytes));
btrfs_discard_update_discardable(block_group);
spin_unlock(&ctl->tree_lock);
spin_unlock(&sinfo->lock);
}
-/* Bytes of whole stripes lying wholly inside [bytenr, bytenr + size). */
-static u64 stripe_interior_bytes(const struct btrfs_block_group *bg,
+/*
+ * Bytes of whole stripes lying wholly inside [bytenr, bytenr + size). Unused
+ * since the incremental positive credit was dropped; kept for reference / a
+ * future credit rule that de-credits its removes symmetrically.
+ */
+static u64 __maybe_unused stripe_interior_bytes(const struct btrfs_block_group *bg,
u64 bytenr, u64 size)
{
const u64 fsl = bg->full_stripe_len;