aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--fs/btrfs/extent-tree.c25
1 files changed, 17 insertions, 8 deletions
diff --git a/fs/btrfs/extent-tree.c b/fs/btrfs/extent-tree.c
index 79365a40cb3a..96cbc5104959 100644
--- a/fs/btrfs/extent-tree.c
+++ b/fs/btrfs/extent-tree.c
@@ -3334,7 +3334,8 @@ out:
3334 * shrink metadata reservation for delalloc 3334 * shrink metadata reservation for delalloc
3335 */ 3335 */
3336static int shrink_delalloc(struct btrfs_trans_handle *trans, 3336static int shrink_delalloc(struct btrfs_trans_handle *trans,
3337 struct btrfs_root *root, u64 to_reclaim, int sync) 3337 struct btrfs_root *root, u64 to_reclaim,
3338 bool wait_ordered)
3338{ 3339{
3339 struct btrfs_block_rsv *block_rsv; 3340 struct btrfs_block_rsv *block_rsv;
3340 struct btrfs_space_info *space_info; 3341 struct btrfs_space_info *space_info;
@@ -3387,11 +3388,15 @@ static int shrink_delalloc(struct btrfs_trans_handle *trans,
3387 if (trans && trans->transaction->blocked) 3388 if (trans && trans->transaction->blocked)
3388 return -EAGAIN; 3389 return -EAGAIN;
3389 3390
3390 time_left = schedule_timeout_interruptible(1); 3391 if (wait_ordered && !trans) {
3392 btrfs_wait_ordered_extents(root, 0, 0);
3393 } else {
3394 time_left = schedule_timeout_interruptible(1);
3391 3395
3392 /* We were interrupted, exit */ 3396 /* We were interrupted, exit */
3393 if (time_left) 3397 if (time_left)
3394 break; 3398 break;
3399 }
3395 3400
3396 /* we've kicked the IO a few times, if anything has been freed, 3401 /* we've kicked the IO a few times, if anything has been freed,
3397 * exit. There is no sense in looping here for a long time 3402 * exit. There is no sense in looping here for a long time
@@ -3406,8 +3411,7 @@ static int shrink_delalloc(struct btrfs_trans_handle *trans,
3406 } 3411 }
3407 3412
3408 } 3413 }
3409 if (reclaimed < to_reclaim && !trans) 3414
3410 btrfs_wait_ordered_extents(root, 0, 0);
3411 return reclaimed >= to_reclaim; 3415 return reclaimed >= to_reclaim;
3412} 3416}
3413 3417
@@ -3438,6 +3442,7 @@ static int reserve_metadata_bytes(struct btrfs_root *root,
3438 int ret = 0; 3442 int ret = 0;
3439 bool committed = false; 3443 bool committed = false;
3440 bool flushing = false; 3444 bool flushing = false;
3445 bool wait_ordered = false;
3441 3446
3442 trans = (struct btrfs_trans_handle *)current->journal_info; 3447 trans = (struct btrfs_trans_handle *)current->journal_info;
3443again: 3448again:
@@ -3496,6 +3501,7 @@ again:
3496 * amount plus the amount of bytes that we need for this 3501 * amount plus the amount of bytes that we need for this
3497 * reservation. 3502 * reservation.
3498 */ 3503 */
3504 wait_ordered = true;
3499 num_bytes = used - space_info->total_bytes + 3505 num_bytes = used - space_info->total_bytes +
3500 (orig_bytes * (retries + 1)); 3506 (orig_bytes * (retries + 1));
3501 } 3507 }
@@ -3530,6 +3536,8 @@ again:
3530 if (used + num_bytes < space_info->total_bytes + avail) { 3536 if (used + num_bytes < space_info->total_bytes + avail) {
3531 space_info->bytes_may_use += orig_bytes; 3537 space_info->bytes_may_use += orig_bytes;
3532 ret = 0; 3538 ret = 0;
3539 } else {
3540 wait_ordered = true;
3533 } 3541 }
3534 } 3542 }
3535 3543
@@ -3552,7 +3560,7 @@ again:
3552 * We do synchronous shrinking since we don't actually unreserve 3560 * We do synchronous shrinking since we don't actually unreserve
3553 * metadata until after the IO is completed. 3561 * metadata until after the IO is completed.
3554 */ 3562 */
3555 ret = shrink_delalloc(trans, root, num_bytes, 1); 3563 ret = shrink_delalloc(trans, root, num_bytes, wait_ordered);
3556 if (ret < 0) 3564 if (ret < 0)
3557 goto out; 3565 goto out;
3558 3566
@@ -3564,6 +3572,7 @@ again:
3564 * so go back around and try again. 3572 * so go back around and try again.
3565 */ 3573 */
3566 if (retries < 2) { 3574 if (retries < 2) {
3575 wait_ordered = true;
3567 retries++; 3576 retries++;
3568 goto again; 3577 goto again;
3569 } 3578 }