aboutsummaryrefslogtreecommitdiffstats
path: root/fs/btrfs/ioctl.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/btrfs/ioctl.c')
-rw-r--r--fs/btrfs/ioctl.c35
1 files changed, 35 insertions, 0 deletions
diff --git a/fs/btrfs/ioctl.c b/fs/btrfs/ioctl.c
index 63600dc2ac4c..d60b6caf09e8 100644
--- a/fs/btrfs/ioctl.c
+++ b/fs/btrfs/ioctl.c
@@ -747,6 +747,7 @@ static int create_snapshot(struct btrfs_root *root, struct inode *dir,
747 struct btrfs_pending_snapshot *pending_snapshot; 747 struct btrfs_pending_snapshot *pending_snapshot;
748 struct btrfs_trans_handle *trans; 748 struct btrfs_trans_handle *trans;
749 int ret; 749 int ret;
750 bool snapshot_force_cow = false;
750 751
751 if (!test_bit(BTRFS_ROOT_REF_COWS, &root->state)) 752 if (!test_bit(BTRFS_ROOT_REF_COWS, &root->state))
752 return -EINVAL; 753 return -EINVAL;
@@ -763,6 +764,11 @@ static int create_snapshot(struct btrfs_root *root, struct inode *dir,
763 goto free_pending; 764 goto free_pending;
764 } 765 }
765 766
767 /*
768 * Force new buffered writes to reserve space even when NOCOW is
769 * possible. This is to avoid later writeback (running dealloc) to
770 * fallback to COW mode and unexpectedly fail with ENOSPC.
771 */
766 atomic_inc(&root->will_be_snapshotted); 772 atomic_inc(&root->will_be_snapshotted);
767 smp_mb__after_atomic(); 773 smp_mb__after_atomic();
768 /* wait for no snapshot writes */ 774 /* wait for no snapshot writes */
@@ -773,6 +779,14 @@ static int create_snapshot(struct btrfs_root *root, struct inode *dir,
773 if (ret) 779 if (ret)
774 goto dec_and_free; 780 goto dec_and_free;
775 781
782 /*
783 * All previous writes have started writeback in NOCOW mode, so now
784 * we force future writes to fallback to COW mode during snapshot
785 * creation.
786 */
787 atomic_inc(&root->snapshot_force_cow);
788 snapshot_force_cow = true;
789
776 btrfs_wait_ordered_extents(root, U64_MAX, 0, (u64)-1); 790 btrfs_wait_ordered_extents(root, U64_MAX, 0, (u64)-1);
777 791
778 btrfs_init_block_rsv(&pending_snapshot->block_rsv, 792 btrfs_init_block_rsv(&pending_snapshot->block_rsv,
@@ -837,6 +851,8 @@ static int create_snapshot(struct btrfs_root *root, struct inode *dir,
837fail: 851fail:
838 btrfs_subvolume_release_metadata(fs_info, &pending_snapshot->block_rsv); 852 btrfs_subvolume_release_metadata(fs_info, &pending_snapshot->block_rsv);
839dec_and_free: 853dec_and_free:
854 if (snapshot_force_cow)
855 atomic_dec(&root->snapshot_force_cow);
840 if (atomic_dec_and_test(&root->will_be_snapshotted)) 856 if (atomic_dec_and_test(&root->will_be_snapshotted))
841 wake_up_var(&root->will_be_snapshotted); 857 wake_up_var(&root->will_be_snapshotted);
842free_pending: 858free_pending:
@@ -3453,6 +3469,25 @@ static int btrfs_extent_same_range(struct inode *src, u64 loff, u64 olen,
3453 3469
3454 same_lock_start = min_t(u64, loff, dst_loff); 3470 same_lock_start = min_t(u64, loff, dst_loff);
3455 same_lock_len = max_t(u64, loff, dst_loff) + len - same_lock_start; 3471 same_lock_len = max_t(u64, loff, dst_loff) + len - same_lock_start;
3472 } else {
3473 /*
3474 * If the source and destination inodes are different, the
3475 * source's range end offset matches the source's i_size, that
3476 * i_size is not a multiple of the sector size, and the
3477 * destination range does not go past the destination's i_size,
3478 * we must round down the length to the nearest sector size
3479 * multiple. If we don't do this adjustment we end replacing
3480 * with zeroes the bytes in the range that starts at the
3481 * deduplication range's end offset and ends at the next sector
3482 * size multiple.
3483 */
3484 if (loff + olen == i_size_read(src) &&
3485 dst_loff + len < i_size_read(dst)) {
3486 const u64 sz = BTRFS_I(src)->root->fs_info->sectorsize;
3487
3488 len = round_down(i_size_read(src), sz) - loff;
3489 olen = len;
3490 }
3456 } 3491 }
3457 3492
3458again: 3493again: