summaryrefslogtreecommitdiffstats
path: root/fs/ext4/resize.c
diff options
context:
space:
mode:
authorTheodore Ts'o <tytso@mit.edu>2012-09-05 01:29:50 -0400
committerTheodore Ts'o <tytso@mit.edu>2012-09-05 01:29:50 -0400
commit117fff10d7f140e12dd43df20d3f9fda80577460 (patch)
tree0236d1dfb77e794b1628b723f21b3c83383e0475 /fs/ext4/resize.c
parent2ebd1704ded88a8ae29b5f3998b13959c715c4be (diff)
downloadlinux-117fff10d7f140e12dd43df20d3f9fda80577460.tar.bz2
ext4: grow the s_flex_groups array as needed when resizing
Previously, we allocated the s_flex_groups array to the maximum size that the file system could be resized. There was two problems with this approach. First, it wasted memory in the common case where the file system was not resized. Secondly, once we start allowing online resizing using the meta_bg scheme, there is no maximum size that the file system can be resized. So instead, we need to grow the s_flex_groups at inline resize time. Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
Diffstat (limited to 'fs/ext4/resize.c')
-rw-r--r--fs/ext4/resize.c14
1 files changed, 9 insertions, 5 deletions
diff --git a/fs/ext4/resize.c b/fs/ext4/resize.c
index 365d800ff8c1..3f5c67bf13a2 100644
--- a/fs/ext4/resize.c
+++ b/fs/ext4/resize.c
@@ -1503,6 +1503,10 @@ int ext4_group_add(struct super_block *sb, struct ext4_new_group_data *input)
if (err)
goto out;
+ err = ext4_alloc_flex_bg_array(sb, input->group + 1);
+ if (err)
+ return err;
+
flex_gd.count = 1;
flex_gd.groups = input;
flex_gd.bg_flags = &bg_flags;
@@ -1662,7 +1666,7 @@ int ext4_resize_fs(struct super_block *sb, ext4_fsblk_t n_blocks_count)
unsigned long n_desc_blocks;
unsigned long o_desc_blocks;
unsigned long desc_blocks;
- int err = 0, flexbg_size = 1;
+ int err = 0, flexbg_size = 1 << sbi->s_log_groups_per_flex;
o_blocks_count = ext4_blocks_count(es);
@@ -1721,13 +1725,13 @@ int ext4_resize_fs(struct super_block *sb, ext4_fsblk_t n_blocks_count)
goto out;
}
- if (EXT4_HAS_INCOMPAT_FEATURE(sb, EXT4_FEATURE_INCOMPAT_FLEX_BG) &&
- es->s_log_groups_per_flex)
- flexbg_size = 1 << es->s_log_groups_per_flex;
-
if (ext4_blocks_count(es) == n_blocks_count)
goto out;
+ err = ext4_alloc_flex_bg_array(sb, n_group + 1);
+ if (err)
+ return err;
+
flex_gd = alloc_flex_gd(flexbg_size);
if (flex_gd == NULL) {
err = -ENOMEM;