btrfs: fix int32 overflow in shrink_delalloc().
diff mbox

Message ID 1462712880-29392-1-git-send-email-kilobyte@angband.pl
State Accepted
Headers show

Commit Message

Adam Borowski May 8, 2016, 1:08 p.m. UTC
UBSAN: Undefined behaviour in fs/btrfs/extent-tree.c:4623:21
signed integer overflow:
10808 * 262144 cannot be represented in type 'int [8]'

If 8192<=items<16384, we request a writeback of an insane number of pages
which is benign (everything will be written).  But if items>=16384, the
space reservation won't be enough.

Signed-off-by: Adam Borowski <kilobyte@angband.pl>
---
 fs/btrfs/extent-tree.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

Comments

David Sterba May 9, 2016, 9:51 a.m. UTC | #1
On Sun, May 08, 2016 at 03:08:00PM +0200, Adam Borowski wrote:
> UBSAN: Undefined behaviour in fs/btrfs/extent-tree.c:4623:21
> signed integer overflow:
> 10808 * 262144 cannot be represented in type 'int [8]'
> 
> If 8192<=items<16384, we request a writeback of an insane number of pages
> which is benign (everything will be written).  But if items>=16384, the
> space reservation won't be enough.
> 
> Signed-off-by: Adam Borowski <kilobyte@angband.pl>

Reviewed-by: David Sterba <dsterba@suse.com>

I think this is the best fix, although I usually do not like to see
random type casts. In this case, we'd have to change items to something
else and propagate the change trhough several functions for no apparent
gain.  Just to satisfy one multiplication.
--
To unsubscribe from this list: send the line "unsubscribe linux-btrfs" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

Patch
diff mbox

diff --git a/fs/btrfs/extent-tree.c b/fs/btrfs/extent-tree.c
index 84e060e..391f576 100644
--- a/fs/btrfs/extent-tree.c
+++ b/fs/btrfs/extent-tree.c
@@ -4620,7 +4620,7 @@  static void shrink_delalloc(struct btrfs_root *root, u64 to_reclaim, u64 orig,
 
 	/* Calc the number of the pages we need flush for space reservation */
 	items = calc_reclaim_items_nr(root, to_reclaim);
-	to_reclaim = items * EXTENT_SIZE_PER_ITEM;
+	to_reclaim = (u64)items * EXTENT_SIZE_PER_ITEM;
 
 	trans = (struct btrfs_trans_handle *)current->journal_info;
 	block_rsv = &root->fs_info->delalloc_block_rsv;