From 4df1618250349dbe71f9474c42d52d7d03cc68a0 Mon Sep 17 00:00:00 2001 From: Theodore Ts'o Date: Fri, 18 Mar 2011 14:47:15 -0400 Subject: [PATCH] add new superblock field: s_overhead_blocks It turns out that it's very hard to calculate overheads in the face of clustered allocation (bigalloc). This is because multiple metadata blocks from different block groups can end up in the same allocation cluster. Calculating the exact overhead requires O(all block bitmaps) in memory, or O(number of block groups**2) in time. So we will calculate this at mkfs time and stash it in the superblock. Signed-off-by: "Theodore Ts'o" --- debugfs/set_fields.c | 1 + lib/e2p/ls.c | 3 +++ lib/ext2fs/ext2_fs.h | 5 +++-- lib/ext2fs/tst_super_size.c | 1 + 4 files changed, 8 insertions(+), 2 deletions(-) diff --git a/debugfs/set_fields.c b/debugfs/set_fields.c index 9d7099b..e4fdeee 100644 --- a/debugfs/set_fields.c +++ b/debugfs/set_fields.c @@ -142,6 +142,7 @@ static struct field_set_info super_fields[] = { { "mount_opts", &set_sb.s_mount_opts, 64, parse_string }, { "usr_quota_inum", &set_sb.s_usr_quota_inum, 4, parse_uint }, { "grp_quota_inum", &set_sb.s_grp_quota_inum, 4, parse_uint }, + { "overhead_blocks", &set_sb.s_overhead_blocks, 4, parse_uint }, { 0, 0, 0, 0 } }; diff --git a/lib/e2p/ls.c b/lib/e2p/ls.c index 04a2c71..6785ced 100644 --- a/lib/e2p/ls.c +++ b/lib/e2p/ls.c @@ -225,6 +225,9 @@ void list_super2(struct ext2_super_block * sb, FILE *f) fprintf(f, "Inode count: %u\n", sb->s_inodes_count); fprintf(f, "Block count: %u\n", sb->s_blocks_count); fprintf(f, "Reserved block count: %u\n", sb->s_r_blocks_count); + if (sb->s_overhead_blocks) + fprintf(f, "Overhead blocks: %u\n", + sb->s_overhead_blocks); fprintf(f, "Free blocks: %u\n", sb->s_free_blocks_count); fprintf(f, "Free inodes: %u\n", sb->s_free_inodes_count); fprintf(f, "First block: %u\n", sb->s_first_data_block); diff --git a/lib/ext2fs/ext2_fs.h b/lib/ext2fs/ext2_fs.h index b4fc6d9..a6c70de 100644 --- a/lib/ext2fs/ext2_fs.h +++ b/lib/ext2fs/ext2_fs.h @@ -515,7 +515,7 @@ struct ext2_super_block { __u32 s_free_inodes_count; /* Free inodes count */ __u32 s_first_data_block; /* First Data Block */ __u32 s_log_block_size; /* Block size */ - __s32 s_log_cluster_size; /* Allocation cluster size */ + __u32 s_log_cluster_size; /* Allocation cluster size */ __u32 s_blocks_per_group; /* # Blocks per group */ __u32 s_clusters_per_group; /* # Fragments per group */ __u32 s_inodes_per_group; /* # Inodes per group */ @@ -613,7 +613,8 @@ struct ext2_super_block { __u8 s_mount_opts[64]; __u32 s_usr_quota_inum; /* inode number of user quota file */ __u32 s_grp_quota_inum; /* inode number of group quota file */ - __u32 s_reserved[110]; /* Padding to the end of the block */ + __u32 s_overhead_blocks; /* overhead blocks/clusters in fs */ + __u32 s_reserved[109]; /* Padding to the end of the block */ }; #define EXT4_S_ERR_LEN (EXT4_S_ERR_END - EXT4_S_ERR_START) diff --git a/lib/ext2fs/tst_super_size.c b/lib/ext2fs/tst_super_size.c index 6fffcfd..1e5a524 100644 --- a/lib/ext2fs/tst_super_size.c +++ b/lib/ext2fs/tst_super_size.c @@ -125,6 +125,7 @@ void check_superblock_fields() check_field(s_mount_opts); check_field(s_usr_quota_inum); check_field(s_grp_quota_inum); + check_field(s_overhead_blocks); check_field(s_reserved); printf("Ending offset is %d\n\n", cur_offset); #endif -- 1.8.3.1