spin_lock(&space_info->lock);
spin_lock(&bg->lock);
- if (bg->reserved || bg->pinned || bg->ro) {
+ if (bg->ro ||
+ ((bg->reserved || bg->pinned) &&
+ !btrfs_is_stripe_alloc_bg(bg) &&
+ !btrfs_is_stripe_meta_bg(bg))) {
/*
* We want to bail if we made new allocations or have
* outstanding allocations in this block group. We do
* the ro check in case balance is currently acting on
* this block group.
+ *
+ * Not for a stripe_alloc or stripe_meta group: under
+ * COW churn it always has blocks reserved or pinned,
+ * so the bail-out would defer it forever, while the
+ * trapped free space it was queued for only grows.
+ * Relocation waits for in-flight allocations itself.
*/
spin_unlock(&bg->lock);
spin_unlock(&space_info->lock);