[PATCH 32/42] btrfs: only free reserved extent if we didn't insert it
When we insert the file extent once the ordered extent completes we free the reserved extent reservation as it'll have been migrated to the bytes_used counter. However if we error out after this step we'll still clear the reserved extent reservation, resulting in a negative accounting of the reserved bytes for the block group and space info. Fix this by only doing the free if we didn't successfully insert a file extent for this extent. Signed-off-by: Josef Bacik Reviewed-by: Omar Sandoval --- fs/btrfs/inode.c | 10 +- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/fs/btrfs/inode.c b/fs/btrfs/inode.c index 5a91055a13b2..2b257d14bd3d 100644 --- a/fs/btrfs/inode.c +++ b/fs/btrfs/inode.c @@ -2992,6 +2992,7 @@ static int btrfs_finish_ordered_io(struct btrfs_ordered_extent *ordered_extent) bool truncated = false; bool range_locked = false; bool clear_new_delalloc_bytes = false; + bool clear_reserved_extent = true; if (!test_bit(BTRFS_ORDERED_NOCOW, _extent->flags) && !test_bit(BTRFS_ORDERED_PREALLOC, _extent->flags) && @@ -3095,10 +3096,12 @@ static int btrfs_finish_ordered_io(struct btrfs_ordered_extent *ordered_extent) logical_len, logical_len, compress_type, 0, 0, BTRFS_FILE_EXTENT_REG); - if (!ret) + if (!ret) { + clear_reserved_extent = false; btrfs_release_delalloc_bytes(fs_info, ordered_extent->start, ordered_extent->disk_len); + } } unpin_extent_cache(_I(inode)->extent_tree, ordered_extent->file_offset, ordered_extent->len, @@ -3159,8 +3162,13 @@ static int btrfs_finish_ordered_io(struct btrfs_ordered_extent *ordered_extent) * wrong we need to return the space for this ordered extent * back to the allocator. We only free the extent in the * truncated case if we didn't write out the extent at all. +* +* If we made it past insert_reserved_file_extent before we +* errored out then we don't need to do this as the accounting +* has already been done. */ if ((ret || !logical_len) && + clear_reserved_extent && !test_bit(BTRFS_ORDERED_NOCOW, _extent->flags) && !test_bit(BTRFS_ORDERED_PREALLOC, _extent->flags)) btrfs_free_reserved_extent(fs_info, -- 2.14.3
Re: [PATCH 32/42] btrfs: only free reserved extent if we didn't insert it
On Thu, Oct 11, 2018 at 8:58 PM Josef Bacik wrote: > > When we insert the file extent once the ordered extent completes we free > the reserved extent reservation as it'll have been migrated to the > bytes_used counter. However if we error out after this step we'll still > clear the reserved extent reservation, resulting in a negative > accounting of the reserved bytes for the block group and space info. > Fix this by only doing the free if we didn't successfully insert a file > extent for this extent. > > Signed-off-by: Josef Bacik > Reviewed-by: Omar Sandoval Reviewed-by: Filipe Manana > --- > fs/btrfs/inode.c | 10 +- > 1 file changed, 9 insertions(+), 1 deletion(-) > > diff --git a/fs/btrfs/inode.c b/fs/btrfs/inode.c > index 5a91055a13b2..2b257d14bd3d 100644 > --- a/fs/btrfs/inode.c > +++ b/fs/btrfs/inode.c > @@ -2992,6 +2992,7 @@ static int btrfs_finish_ordered_io(struct > btrfs_ordered_extent *ordered_extent) > bool truncated = false; > bool range_locked = false; > bool clear_new_delalloc_bytes = false; > + bool clear_reserved_extent = true; > > if (!test_bit(BTRFS_ORDERED_NOCOW, _extent->flags) && > !test_bit(BTRFS_ORDERED_PREALLOC, _extent->flags) && > @@ -3095,10 +3096,12 @@ static int btrfs_finish_ordered_io(struct > btrfs_ordered_extent *ordered_extent) > logical_len, logical_len, > compress_type, 0, 0, > BTRFS_FILE_EXTENT_REG); > - if (!ret) > + if (!ret) { > + clear_reserved_extent = false; > btrfs_release_delalloc_bytes(fs_info, > ordered_extent->start, > > ordered_extent->disk_len); > + } > } > unpin_extent_cache(_I(inode)->extent_tree, >ordered_extent->file_offset, ordered_extent->len, > @@ -3159,8 +3162,13 @@ static int btrfs_finish_ordered_io(struct > btrfs_ordered_extent *ordered_extent) > * wrong we need to return the space for this ordered extent > * back to the allocator. We only free the extent in the > * truncated case if we didn't write out the extent at all. > +* > +* If we made it past insert_reserved_file_extent before we > +* errored out then we don't need to do this as the accounting > +* has already been done. > */ > if ((ret || !logical_len) && > + clear_reserved_extent && > !test_bit(BTRFS_ORDERED_NOCOW, _extent->flags) && > !test_bit(BTRFS_ORDERED_PREALLOC, _extent->flags)) > btrfs_free_reserved_extent(fs_info, > -- > 2.14.3 > -- Filipe David Manana, “Whether you think you can, or you think you can't — you're right.”
[PATCH 32/42] btrfs: only free reserved extent if we didn't insert it
When we insert the file extent once the ordered extent completes we free the reserved extent reservation as it'll have been migrated to the bytes_used counter. However if we error out after this step we'll still clear the reserved extent reservation, resulting in a negative accounting of the reserved bytes for the block group and space info. Fix this by only doing the free if we didn't successfully insert a file extent for this extent. Signed-off-by: Josef Bacik Reviewed-by: Omar Sandoval --- fs/btrfs/inode.c | 10 +- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/fs/btrfs/inode.c b/fs/btrfs/inode.c index 5a91055a13b2..2b257d14bd3d 100644 --- a/fs/btrfs/inode.c +++ b/fs/btrfs/inode.c @@ -2992,6 +2992,7 @@ static int btrfs_finish_ordered_io(struct btrfs_ordered_extent *ordered_extent) bool truncated = false; bool range_locked = false; bool clear_new_delalloc_bytes = false; + bool clear_reserved_extent = true; if (!test_bit(BTRFS_ORDERED_NOCOW, _extent->flags) && !test_bit(BTRFS_ORDERED_PREALLOC, _extent->flags) && @@ -3095,10 +3096,12 @@ static int btrfs_finish_ordered_io(struct btrfs_ordered_extent *ordered_extent) logical_len, logical_len, compress_type, 0, 0, BTRFS_FILE_EXTENT_REG); - if (!ret) + if (!ret) { + clear_reserved_extent = false; btrfs_release_delalloc_bytes(fs_info, ordered_extent->start, ordered_extent->disk_len); + } } unpin_extent_cache(_I(inode)->extent_tree, ordered_extent->file_offset, ordered_extent->len, @@ -3159,8 +3162,13 @@ static int btrfs_finish_ordered_io(struct btrfs_ordered_extent *ordered_extent) * wrong we need to return the space for this ordered extent * back to the allocator. We only free the extent in the * truncated case if we didn't write out the extent at all. +* +* If we made it past insert_reserved_file_extent before we +* errored out then we don't need to do this as the accounting +* has already been done. */ if ((ret || !logical_len) && + clear_reserved_extent && !test_bit(BTRFS_ORDERED_NOCOW, _extent->flags) && !test_bit(BTRFS_ORDERED_PREALLOC, _extent->flags)) btrfs_free_reserved_extent(fs_info, -- 2.14.3
[PATCH 32/42] btrfs: only free reserved extent if we didn't insert it
When we insert the file extent once the ordered extent completes we free the reserved extent reservation as it'll have been migrated to the bytes_used counter. However if we error out after this step we'll still clear the reserved extent reservation, resulting in a negative accounting of the reserved bytes for the block group and space info. Fix this by only doing the free if we didn't successfully insert a file extent for this extent. Signed-off-by: Josef Bacik Reviewed-by: Omar Sandoval --- fs/btrfs/inode.c | 10 +- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/fs/btrfs/inode.c b/fs/btrfs/inode.c index 5a91055a13b2..2b257d14bd3d 100644 --- a/fs/btrfs/inode.c +++ b/fs/btrfs/inode.c @@ -2992,6 +2992,7 @@ static int btrfs_finish_ordered_io(struct btrfs_ordered_extent *ordered_extent) bool truncated = false; bool range_locked = false; bool clear_new_delalloc_bytes = false; + bool clear_reserved_extent = true; if (!test_bit(BTRFS_ORDERED_NOCOW, _extent->flags) && !test_bit(BTRFS_ORDERED_PREALLOC, _extent->flags) && @@ -3095,10 +3096,12 @@ static int btrfs_finish_ordered_io(struct btrfs_ordered_extent *ordered_extent) logical_len, logical_len, compress_type, 0, 0, BTRFS_FILE_EXTENT_REG); - if (!ret) + if (!ret) { + clear_reserved_extent = false; btrfs_release_delalloc_bytes(fs_info, ordered_extent->start, ordered_extent->disk_len); + } } unpin_extent_cache(_I(inode)->extent_tree, ordered_extent->file_offset, ordered_extent->len, @@ -3159,8 +3162,13 @@ static int btrfs_finish_ordered_io(struct btrfs_ordered_extent *ordered_extent) * wrong we need to return the space for this ordered extent * back to the allocator. We only free the extent in the * truncated case if we didn't write out the extent at all. +* +* If we made it past insert_reserved_file_extent before we +* errored out then we don't need to do this as the accounting +* has already been done. */ if ((ret || !logical_len) && + clear_reserved_extent && !test_bit(BTRFS_ORDERED_NOCOW, _extent->flags) && !test_bit(BTRFS_ORDERED_PREALLOC, _extent->flags)) btrfs_free_reserved_extent(fs_info, -- 2.14.3